@@ -194,6 +194,8 @@ fn (mut d DenseArray) zeros_to_end() {
194194}
195195
196196pub struct map {
197+ // Number of bytes of a key
198+ key_bytes int
197199 // Number of bytes of a value
198200 value_bytes int
199201mut :
@@ -219,12 +221,14 @@ pub mut:
219221
220222fn new_map_1 (value_bytes int ) map {
221223 metasize := int (sizeof (u32 ) * (init_capicity + extra_metas_inc))
224+ key_bytes := int (sizeof (string ))
222225 return map {
226+ key_bytes: key_bytes
223227 value_bytes: value_bytes
224228 cap: init_cap
225229 cached_hashbits: max_cached_hashbits
226230 shift: init_log_capicity
227- key_values: new_dense_array (int ( sizeof ( string )) , value_bytes)
231+ key_values: new_dense_array (key_bytes , value_bytes)
228232 metas: & u32 (vcalloc (metasize))
229233 extra_metas: extra_metas_inc
230234 len: 0
@@ -240,7 +244,14 @@ fn new_map_init(n int, value_bytes int, keys &string, values voidptr) map {
240244}
241245
242246[inline ]
243- fn (m &map) key_to_index (key string ) (u32 , u32 ) {
247+ fn (m &map) keys_eq (a voidptr , b voidptr ) bool {
248+ // assume string for now
249+ return fast_string_eq (* & string (a), * & string (b))
250+ }
251+
252+ [inline ]
253+ fn (m &map) key_to_index (pkey voidptr ) (u32 , u32 ) {
254+ key := * & string (pkey)
244255 hash := hash.wyhash_c (key.str, u64 (key.len), 0 )
245256 index := hash & m.cap
246257 meta := ((hash >> m.shift) & hash_mask) | probe_inc
@@ -311,23 +322,23 @@ fn (mut m map) set(k string, value voidptr) {
311322 if load_factor > max_load_factor {
312323 m.expand ()
313324 }
314- mut index, mut meta := m.key_to_index (key)
325+ mut index, mut meta := m.key_to_index (& key)
315326 index , meta = m.meta_less (index, meta)
316327 // While we might have a match
317328 for meta == unsafe {m.metas[index]} {
318329 kv_index := int (unsafe {m.metas[index + 1 ]})
319- pkey := unsafe {& string ( m.key_values.key (kv_index) )}
320- if fast_string_eq ( key, * pkey) {
330+ pkey := unsafe {m.key_values.key (kv_index)}
331+ if m. keys_eq ( & key, pkey) {
321332 unsafe {
322- pval := pkey + 1 // skip string
333+ pval := byteptr ( pkey) + m.key_bytes
323334 C.memcpy (pval, value, m.value_bytes)
324335 }
325336 return
326337 }
327338 index + = 2
328339 meta + = probe_inc
329340 }
330- kv_index := m.key_values.push (key, value)
341+ kv_index := m.key_values.push (& key, value)
331342 m.meta_greater (index, meta, u32 (kv_index))
332343 m.len++
333344}
@@ -363,8 +374,8 @@ fn (mut m map) rehash() {
363374 if ! m.key_values.has_index (i) {
364375 continue
365376 }
366- pkey := unsafe {& string ( m.key_values.key (i) )}
367- mut index, mut meta := m.key_to_index (* pkey)
377+ pkey := unsafe {m.key_values.key (i)}
378+ mut index, mut meta := m.key_to_index (pkey)
368379 index , meta = m.meta_less (index, meta)
369380 m.meta_greater (index, meta, u32 (i))
370381 }
@@ -398,12 +409,12 @@ fn (mut m map) cached_rehash(old_cap u32) {
398409// If the key exists, its respective value is returned.
399410fn (mut m map) get_and_set (key string , zero voidptr ) voidptr {
400411 for {
401- mut index, mut meta := m.key_to_index (key)
412+ mut index, mut meta := m.key_to_index (& key)
402413 for {
403414 if meta == unsafe {m.metas[index]} {
404415 kv_index := int (unsafe {m.metas[index + 1 ]})
405- pkey := unsafe {& string ( m.key_values.key (kv_index) )}
406- if fast_string_eq ( key, * pkey) {
416+ pkey := unsafe {m.key_values.key (kv_index)}
417+ if m. keys_eq ( & key, pkey) {
407418 return unsafe {byteptr (pkey) + m.key_values.key_bytes}
408419 }
409420 }
@@ -424,12 +435,12 @@ fn (mut m map) get_and_set(key string, zero voidptr) voidptr {
424435// the method returns a reference to its mapped value.
425436// If not, a zero/default value is returned.
426437fn (m map) get (key string , zero voidptr ) voidptr {
427- mut index, mut meta := m.key_to_index (key)
438+ mut index, mut meta := m.key_to_index (& key)
428439 for {
429440 if meta == unsafe {m.metas[index]} {
430441 kv_index := int (unsafe {m.metas[index + 1 ]})
431- pkey := unsafe {& string ( m.key_values.key (kv_index) )}
432- if fast_string_eq ( key, * pkey) {
442+ pkey := unsafe {m.key_values.key (kv_index)}
443+ if m. keys_eq ( & key, pkey) {
433444 return unsafe {byteptr (pkey) + m.key_values.key_bytes}
434445 }
435446 }
@@ -444,12 +455,12 @@ fn (m map) get(key string, zero voidptr) voidptr {
444455
445456// Checks whether a particular key exists in the map.
446457fn (m map) exists (key string ) bool {
447- mut index, mut meta := m.key_to_index (key)
458+ mut index, mut meta := m.key_to_index (& key)
448459 for {
449460 if meta == unsafe {m.metas[index]} {
450461 kv_index := int (unsafe {m.metas[index + 1 ]})
451- pkey := unsafe {& string ( m.key_values.key (kv_index) )}
452- if fast_string_eq ( key, * pkey) {
462+ pkey := unsafe {m.key_values.key (kv_index)}
463+ if m. keys_eq ( & key, pkey) {
453464 return true
454465 }
455466 }
@@ -464,13 +475,13 @@ fn (m map) exists(key string) bool {
464475
465476// Removes the mapping of a particular key from the map.
466477pub fn (mut m map) delete (key string ) {
467- mut index, mut meta := m.key_to_index (key)
478+ mut index, mut meta := m.key_to_index (& key)
468479 index , meta = m.meta_less (index, meta)
469480 // Perform backwards shifting
470481 for meta == unsafe {m.metas[index]} {
471482 kv_index := int (unsafe {m.metas[index + 1 ]})
472483 pkey := unsafe {& string (m.key_values.key (kv_index))}
473- if fast_string_eq ( key, * pkey) {
484+ if m. keys_eq ( & key, pkey) {
474485 for (unsafe {m.metas[index + 2 ]} >> hashbits) > 1 {
475486 unsafe {
476487 m.metas[index] = m.metas[index + 2 ] - probe_inc
@@ -554,6 +565,7 @@ pub fn (d DenseArray) clone() DenseArray {
554565pub fn (m map) clone () map {
555566 metasize := int (sizeof (u32 ) * (m.cap + 2 + m.extra_metas))
556567 res := map {
568+ key_bytes: m.key_bytes
557569 value_bytes: m.value_bytes
558570 cap: m.cap
559571 cached_hashbits: m.cached_hashbits
0 commit comments