A couple of questions about arrays and slices

Cecil Ward cecil at cecilward.com
Sat Jun 24 07:36:26 UTC 2023


On Saturday, 24 June 2023 at 01:28:03 UTC, Jonathan M Davis wrote:
> On Friday, June 23, 2023 7:02:12 PM MDT Cecil Ward via 
> Digitalmars-d-learn wrote:
>> I just had a fight with LDC over the following code when I 
>> tried out reserve. I have an associative array that maps 
>> strings to ‘ordinals’ ie uints that are unique, and the 
>> compiler hates the call to reserve.
>>
>> ==
>>
>>
>>
>> struct decls_t
>>   {
>>   uint                        n_entries = 0;
>>   uint[ dstring ]     ordinals;   // Associative array maps 
>> variable
>> names to ordinals
>>   }
>>
>> static decls_t Decls;
>>
>> enum NPreAllocEntries = 32;
>> Decls.ordinals.reserve( NPreAllocEntries );
>>
>> source>(82): Error: none of the overloads of template
>> `object.reserve` are callable using argument types
>> `!()(uint[dstring], ulong)`
>> /opt/compiler-explorer/ldc1.32.1/ldc2-1.32.1-linux-x86_64/bin/../import/obje
>> ct.d(3983):        Candidate is: `reserve(T)(ref T[] arr, 
>> size_t
>> newcapacity)` Compiler returned: 1
>
> Associative arrays and dynamic arrays are completely different 
> things. Associative arrays are hash tables, and reserve really 
> doesn't make sense for them. reserve is for telling the GC to 
> make sure that a dynamic array has at least a specific amount 
> of room to grow into before the GC needs to do a reallocation 
> so that the dynamic array refers to a different memory block 
> with enough memory to hold the data, whereas if and when 
> associative arrays have to reallocate any of their internals is 
> largely implementation-defined.
>
> Any time that you add or remove elements from an AA, it might 
> reallocate some of its internals depending on its current state 
> and what the key of the element is - and that could be 
> different between different compiler releases (though it's 
> unlikely to change very often, since I don't think that the AA 
> implementation gets messed with much).
>
> You can use the rehash function on AAs to tell the GC to try to 
> reorder how it's structured all of its buckets so that lookups 
> are more efficient with the data that's currently in there, and 
> you can call clear to remove all its elements, but in general, 
> you don't do much to manage an AA's memory. It's a much more 
> complicated data structure than an array.
>
> https://dlang.org/spec/hash-map.html
>
> - Jonathan M Davis

Jonathan, is it possible that I wanted one thing and got another? 
My description in the earlier post was of the _aim_ of the 
program. What I ended up with might be something else? I wanted 
an array of uints whose values are the results/outputs of the 
mapping function. Since it is keyed by strings I assumed that the 
runtime generates some kind of hash for fast lookup when I ask it 
to retrieve an entry by the string (key) associated with it. I 
assumed that in some sense the hashing was sort of separate with 
some degree of independence from the underlying array, if that 
makes sense. The lookup is just assumed to be fast but how it is 
done we don’t really care. I just wanted to expand the array as I 
did successfully elsewhere with reserve, as I built this 
structure by successive additions of data. I have a number of 
strings and the map is meant to output the ordinal number in 
which I first saw them, zero-based. Then I want to come back and 
randomly look up one ordinal given a string preferably with a 
very fast lookup. The number of entries can not practically be 
more than 30, and even that would be highly unusual, maybe ten is 
the practical limit in my particular case, so it’s hardly MySQL.


More information about the Digitalmars-d-learn mailing list