improve dict perf

This commit is contained in:
blueloveTH 2024-12-13 14:32:42 +08:00
parent d1ebff587c
commit 4cdbc426d5

View File

@ -99,12 +99,14 @@ static bool Dict__try_get(Dict* self, py_TValue* key, DictEntry** out) {
int idx2 = self->indices[idx]._[i]; int idx2 = self->indices[idx]._[i];
if(idx2 == -1) continue; if(idx2 == -1) continue;
DictEntry* entry = c11__at(DictEntry, &self->entries, idx2); DictEntry* entry = c11__at(DictEntry, &self->entries, idx2);
int res = py_equal(&entry->key, key); if(entry->hash == (uint64_t)hash) {
if(res == 1) { int res = py_equal(&entry->key, key);
*out = entry; if(res == 1) {
return true; *out = entry;
return true;
}
if(res == -1) return false; // error
} }
if(res == -1) return false; // error
} }
*out = NULL; *out = NULL;
return true; return true;
@ -195,12 +197,16 @@ static bool Dict__set(Dict* self, py_TValue* key, py_TValue* val) {
} }
// update existing entry // update existing entry
DictEntry* entry = c11__at(DictEntry, &self->entries, idx2); DictEntry* entry = c11__at(DictEntry, &self->entries, idx2);
int res = py_equal(&entry->key, key); // check if they have the same hash
if(res == 1) { if(entry->hash == (uint64_t)hash) {
entry->val = *val; // check if they are equal
return true; int res = py_equal(&entry->key, key);
if(res == 1) {
entry->val = *val;
return true;
}
if(res == -1) return false; // error
} }
if(res == -1) return false; // error
} }
// no empty slot found // no empty slot found
if(self->capacity >= (uint32_t)self->entries.length * 10) { if(self->capacity >= (uint32_t)self->entries.length * 10) {
@ -224,16 +230,18 @@ static int Dict__pop(Dict* self, py_Ref key) {
int idx2 = self->indices[idx]._[i]; int idx2 = self->indices[idx]._[i];
if(idx2 == -1) continue; if(idx2 == -1) continue;
DictEntry* entry = c11__at(DictEntry, &self->entries, idx2); DictEntry* entry = c11__at(DictEntry, &self->entries, idx2);
int res = py_equal(&entry->key, key); if(entry->hash == (uint64_t)hash) {
if(res == 1) { int res = py_equal(&entry->key, key);
*py_retval() = entry->val; if(res == 1) {
py_newnil(&entry->key); *py_retval() = entry->val;
self->indices[idx]._[i] = -1; py_newnil(&entry->key);
self->length--; self->indices[idx]._[i] = -1;
if(self->length < self->entries.length / 2) Dict__compact_entries(self); self->length--;
return 1; if(self->length < self->entries.length / 2) Dict__compact_entries(self);
return 1;
}
if(res == -1) return -1; // error
} }
if(res == -1) return -1; // error
} }
return 0; return 0;
} }
@ -382,12 +390,16 @@ static bool dict__eq__(int argc, py_Ref argv) {
py_newbool(py_retval(), false); py_newbool(py_retval(), false);
return true; return true;
} }
int res = py_equal(&entry->val, &other_entry->val); if(entry->hash != other_entry->hash) {
if(res == -1) return false;
if(!res) {
py_newbool(py_retval(), false); py_newbool(py_retval(), false);
return true; return true;
} }
int res = py_equal(&entry->val, &other_entry->val);
if(res == 0) {
py_newbool(py_retval(), false);
return true;
}
if(res == -1) return false; // error
} }
py_newbool(py_retval(), true); py_newbool(py_retval(), true);
return true; return true;