{"record":{"id":"29ce0c0bb8d3f3cd","repo":"stride3d/stride","slug":"an-element-with-the-same-key-has-already-been-added","errorCode":null,"errorMessage":"An element with the same key has already been added.","messagePattern":"An element with the same key has already been added\\.","errorType":"exception","errorClass":"ArgumentException","httpStatus":null,"severity":"error","filePath":"sources/core/Stride.Core/Collections/IndexingDictionary.cs","lineNumber":117,"sourceCode":"                ++arrayIndex;\n            }\n            ++index;\n        }\n    }\n\n    public bool Remove(KeyValuePair<int, T> item)\n    {\n        return SafeGet(item.Key) == item.Value && Remove(item.Key);\n    }\n\n    public bool ContainsKey(int index)\n    {\n        return SafeGet(index) != null;\n    }\n\n    public void Add(int key, T value)\n    {\n        if (SafeGet(key) != null) throw new ArgumentException(\"An element with the same key has already been added.\");\n        SafeSet(key, value);\n    }\n\n    public bool Remove(int index)\n    {\n        if (index < 0 || index >= items.Count)\n            return false;\n\n        if (items[index] == null)\n            return false;\n\n        items[index] = null;\n        --Count;\n        index = items.Count - 1;\n        while (index >= 0 && items[index] == null)\n        {\n            items.RemoveAt(index);\n            --index;","sourceCodeStart":99,"sourceCodeEnd":135,"githubUrl":"https://github.com/stride3d/stride/blob/96fad776d210c221682aac1ccdf4c79dc046fc38/sources/core/Stride.Core/Collections/IndexingDictionary.cs#L99-L135","documentation":"IndexingDictionary.Add checks whether the slot for the given int key already holds an item via SafeGet and throws ArgumentException when it does. The dictionary intentionally requires Remove/insert semantics rather than silent overwrite. The indexer (this[key]) must be used to replace an existing value.","triggerScenarios":"Calling Add(key, value) on an IndexingDictionary<int,T> where that key already has a non-null entry; re-adding a key that was previously set through the indexer without removing it first.","commonSituations":"Populating the dictionary from a data source that contains duplicate keys (e.g. duplicate asset IDs); retrying initialization code after a partial failure so the same key is added twice; confusing Add with the indexer which overwrites.","solutions":["Use the indexer dict[key] = value to assign an existing key instead of Add","Check ContainsKey(key) (or null-check via SafeGet) before calling Add","Remove the existing entry with Remove(key) before re-adding","Deduplicate the input data by key before populating the dictionary"],"exampleFix":"// before\ndictionary.Add(id, item); // throws if id already present\n// after\ndictionary[id] = item; // inserts or overwrites","handlingStrategy":"validation","validationCode":"if (!dict.ContainsKey(key)) dict.Add(key, value);","typeGuard":null,"tryCatchPattern":"try { dict.Add(key, value); } catch (ArgumentException) { dict[key] = value; } // or skip","preventionTips":["Prefer indexer assignment when overwrite semantics are desired","Deduplicate input by key before populating","Never assume Add overwrites; check ContainsKey first"],"tags":["csharp","collections","duplicate-key"],"backgroundTag":"file-already-exists","analyzedSha":"96fad776d210c221682aac1ccdf4c79dc046fc38","analyzedAt":"2026-09-14T02:59:31.279Z","contentChangedAt":"2026-09-14T02:59:31.279Z","schemaVersion":2},"datasetVersion":"2026-09-16T04:17:20.429Z"}