January 17, 2005
The issue was never about 'in' ... it was about the read-only semantics of

foo = myAA ['key'];
if (foo)
..

which actually modifies the 'myAA' with an empty key, if the entry did not exist prior to the read operation. Of course, this means that your code will break the next time this key is used (since there's now a bogus entry present).

Question: if you performed a read operation on any other kind of array, would you expect the content to be modified? If you read from a file, would you expect the file-length the change? To say that this AA behavior departs from convention would be something of an understatement.

It used to be that two hash-table lookups were needed to retrieve an entry, when one wished to avoid this bizzare and contrary behavior. Recently, Walter removed the necessity for the two lookups ...

I'd call that a band-aid on a kludge. But that's just my opinion. Yes, it is nice having AA as part of the language core. Yes, it is convenient to avoid a cast from Object to the class type contained. Yes, there is some value in having a single AA container for both classes and native types. The price for this, in Walter's apparent view, is to break one of the most fundamental rules regarding read-only behavior (using AA purely as an rValue, treats it like an lValue also). I'd say that's a rather high price to pay -- I mean, it's only an associative array -- not the failover system for a nuclear reactor ... why introduce, in the core language, such a sneaky mechanism to break seemingly valid code?

http://www.digitalmars.com/drn-bin/wwwnews?digitalmars.D.dtl/124


In article <csfsgn$q3s$1@digitaldaemon.com>, Chris Sauls says...
>
>In article <csek55$2kef$1@digitaldaemon.com>, Paul Bonser says...
>>
>>Chris Sauls wrote:
>>> In article <cscvje$10aa$1@digitaldaemon.com>, Paul Bonser says...
>>> 
>>>>How about an isset() function, like in PHP? To check if there is a key set. Something like:
>>>>
>>>>if (myArray.isset("key"))
>>>>	...
>>> 
>>> 
>>> The following works currently:
>>> #
>>> # if (("key" in myArray) == null)
>>> #
>>> 
>>> -- Chris S
>>> 
>>> 
>>
>>And that doesn't add an empty item named "key"?
>>
>>-PIB
>
>No it sure doesn't.  To check for certain I tossed together this little test. Compiled and ran with DMD 0.110 and found that in-expressions do /not/ add empty items.
>
>-- Chris Sauls
>
>
>
>module aatest;
>
>import std.stdio;
>
>void main() {
>char[][char[]] map;
>char[]* value;
>
>writefln("\nStart");
>writefln("map.length == ", map.length);
>
>value = "foo" in map;
>writefln("\nUsing 'in' the first time");
>writefln("foo in map == ", value == null ? "null" : *value);
>writefln("map.length == ", map.length);
>
>map["foo"] = "abc";
>value = "foo" in map;
>writefln("\nAdding item, using 'in' the second time");
>writefln("foo in map == ", value == null ? "null" : *value);
>writefln("map.length == ", map.length);
>
>delete map["foo"];
>value = "foo" in map;
>writefln("\nDeleting item, using 'in' the third time");
>writefln("foo in map == ", value == null ? "null" : *value);
>writefln("map.length == ", map.length);
>}
>
>


January 17, 2005
Kris wrote:

> Question: if you performed a read operation on any other kind of array, would
> you expect the content to be modified? If you read from a file, would you expect
> the file-length the change? To say that this AA behavior departs from convention
> would be something of an understatement.

Hopefully, the current behaviour is a bug that will eventually be fixed
and not a broken design? (not that it really matters in the meantime...)

Unfortunately, it seems to work as intended:

> /*************************************************
>  * Get pointer to value in associative array indexed by key.
>  * Add entry for key if it is not already there.
>  */
> 
> void *_aaGet(aaA*[] *aa, TypeInfo keyti, int valuesize, ...)

versus

> /*************************************************
>  * Determine if key is in aa.
>  * Returns:
>  *	null	not in aa
>  *	!=null	in aa, return pointer to value
>  */
> 
> void* _aaIn(aaA*[] aa, TypeInfo keyti, ...)

Which means that currently you must use "in" with associative arrays,
just as you must use "is" when comparing object pointers for identity.

I still don't get *why* it's a good idea to create it, if it is missing?

--anders
January 17, 2005
Ruby does something with it hash types that I think is good. The constructor of the hash takes a function that provides the default behaviour when a key is not found.  Associative arrays in D do not have constructors but it could be an attribute.

// throw exception
int[char[]] theMap;
theMap.onKeyNotFound =
delegate(int[char[]] map, char[] key) { throw KeyNotFoundError(); }

// return default value
int[char[]] theMap;
theMap.onKeyNotFound =
delegate(int[char[]] map, char[] key) { return 0; }

// Add it to the assoc array
int[char[]] theMap;
theMap.onKeyNotFound =
delegate(int[char[]] map, char[] key) { map[key] = 0; return 0; }






1 2 3 4
Next ›   Last »