Note that the number of entries in table zzz_names is 386, not 1, as expected. Furthermore, zz_names–>1 seems to evaluate to zero, not the word address for ‘aaa’, as expected. [edited to reverse erroneous edit]
Is it not considered legal in I6 (v6.31) to declare a table array with just one entry? If so, how is the compiler interpreting this declaration in such a way as to not produce an error?
There are two forms of the Array declaration (see §2.4):
! 52 entries, initialized to zero
Array pack_of_cards --> 52;
! 6 entries, initialized as shown
Array small_primes --> 2 3 5 7 11 13;
If there’s one entry after the --> / table keyword, the compiler assumes you mean the first form, even if the entry is not a literal integer. (All literals in I6 have integer values, obviously.)
Really, this should throw an error, since the integer value of 'aaa' is not known until backpatch time. When I test it, I sometimes get an error like:
An array must have between 1 and 32767 entries
But not always. There may be an uninitialized variable lurking in the code.
In any case, you don’t want N entries initialized to zero, so don’t do that.
The upshot is that there’s no way to define a one-entry array whose value is initialized to a specific value. If that was your question, that’s the answer. :)
@zarf, [edit] I’ve now thoroughly confused things by editing and reversing edits for my original question and correcting my answer here; my apologies for the confusion.
I was hoping for a single-entry table-style array, such that: zzz_names–>0 == 1 (to indicate the number of entries) and zzz_names–>1 == ‘aaa’ (the value of the single entry).
If I’m understanding you correctly, you’re saying that the compiler treats ‘table’ and ‘–>’ interchangeably, and decides how to structure things based on the number of entries. I don’t think I am understanding correctly, because shouldn’t
Array names1 --> 'aaa' 'bbb';
produce something different from
Array names2 table 'aaa' 'bbb';
? I would think names1–>0 == ‘aaa’ and names2–>0 == 2 in those cases.
@zarf, OK. That’s what I had thought from reading the manual, which was why I was thinking that
Array zzz_names table 'aaa';
would create an array with entries zzz_names–>0 == 1 and zzz_names–>1 == ‘aaa’, but it doesn’t.
Your second response makes it sound like there’s a possible compiler bug. If so, I would like to report it, but is the issue that it’s not creating a table-style array, or that it should properly decide to treat the “table” keyword as being equivalent to “–>” because there is only one entry? (I would hope for the former.)
I see I’m explaining this badly. The compiler first determines how many entries you want (N) by looking at the value or values after the keyword. Then it generates the array, adding one initial entry if the keyword is table.
The compiler bug is that it should detect that line of code as an error, because N should be the integer value of 'aaa', but that value can’t be known until later in compilation. I’m not sure what value it’s using. It might be a temporary marker for an unresolved dictionary word. It might be uninitialized.
@zarf, Ah. Now I think I understand. The address value of ‘aaa’ should be interpreted such that the line of code means “make a table-style array with entries” along the same pattern as:
Array zzz_names table 5;
And, if I’m understanding correctly, you’re saying that it does do that, only with some random value instead of the (unknown at the time) address value of ‘aaa’. (And the compiler trying to do this before knowing the address of ‘aaa’ would be the bug.)
Thank you for your patience in explaining the details, and, again, my apologies for confusing the issue.
At least according to the manual, this ought to be the result:
Array a1 --> 5; ! produces array with 5 elements 0..4, init to zero
Array a2 --> 5 6; ! produces array with 2 elements -->0=5, -->1=6
Array a3 table 5; ! produces array with 2 elements -->0=1, -->1=5
Array a4 table 5 6; ! produces array with 3 elements -->0=2, -->1=5, -->2=6
If that’s not what it’s actually doing (in particular, if the third form is interpreted as creating 6 elements, as you appear to be suggesting), then that seems like a compiler bug.
Only the first form should be unsafe to use with a dictionary word or other late-patched value.
(sigh) I can’t seem to type a proper sentence on this thread! For the benefit of anyone coming along in the future, I meant to type “The address value of ‘aaa’ should be interpreted such that the line of code means ‘make a table-style array with this many blank entries’ along the same pattern as…” (which, based on his answer, zarf correctly inferred, despite the lack of clarity).
Thanks again, zarf.
@mirality, Yes, the behavior you describe for the third form was what I was expecting, because I wasn’t thinking that ‘aaa’ would be interpreted as its literal value. The top of DM4 page 43 is explicit about that particular syntax, though. I agree that it seems more intuitive for it to work as you describe in the third form.
then foo1 and foo2 have the same address. This doesn’t violate any rules of the language and it wouldn’t cause any unexpected problems for “normal” array use. Of course accessing any elements of foo1 will cause a runtime error, if strict mode is on. That’s consistent with normal array rules.
Even better! And thank you for adding that, because, since you had chosen table [ 5 ] in your original example of the use of brackets (coincidentally the same number as the table 5 of my previous post), I hadn’t realized that there would be a significant difference in interpretation as a result of adding them.