diff --git a/second-part/hw-01/src/app/src/main/java/org/example/MyHashMap.java b/second-part/hw-01/src/app/src/main/java/org/example/MyHashMap.java new file mode 100644 index 0000000..ac5cedf --- /dev/null +++ b/second-part/hw-01/src/app/src/main/java/org/example/MyHashMap.java @@ -0,0 +1,120 @@ +package org.example; + +public class MyHashMap { + + private Key[] keys; + private Value[] values; + private boolean[] deleted; + private int size; + + public MyHashMap(int capacity) { + keys = createArray(capacity); + values = createArray(capacity); + deleted = new boolean[capacity]; + } + + public Value get(Key key) { + int index = findIndex(key); + + return index == -1 ? null : values[index]; + } + + public Value put(Key key, Value value) { + if (size == keys.length) { + resize(); + } + + int index = findEmptyIndex(key); + if (keys[index] != null) { + Value oldValue = values[index]; + values[index] = value; + return oldValue; + } + + keys[index] = key; + values[index] = value; + deleted[index] = false; + size++; + + return null; + } + + public Value remove(Key key) { + int index = findIndex(key); + + if (index == -1) { + return null; + } + + Value oldValue = values[index]; + deleted[index] = true; + size--; + + return oldValue; + } + + private int findIndex(Key key) { + int index = index(key); + int start = index; + + while (keys[index] != null || deleted[index]) { + if (!deleted[index] && java.util.Objects.equals(keys[index], key)) { + return index; + } + + index = (index + 1) % keys.length; + + if (index == start) { + return -1; + } + } + + return -1; + } + + private int findEmptyIndex(Key key) { + int index = index(key); + int start = index; + + while (keys[index] != null && !deleted[index]) { + if (java.util.Objects.equals(keys[index], key)) { + return index; + } + + index = (index + 1) % keys.length; + + if (index == start) { + resize(); + return findEmptyIndex(key); + } + } + + return index; + } + + private int index(Key key) { + return Math.floorMod(key == null ? 0 : key.hashCode(), keys.length); + } + + private void resize() { + Key[] oldKeys = keys; + Value[] oldValues = values; + boolean[] oldDeleted = deleted; + + keys = createArray(oldKeys.length * 2); + values = createArray(oldValues.length * 2); + deleted = new boolean[keys.length]; + size = 0; + + for (int i = 0; i < oldKeys.length; i++) { + if (oldKeys[i] != null && !oldDeleted[i]) { + put(oldKeys[i], oldValues[i]); + } + } + } + + @SuppressWarnings("unchecked") + private T[] createArray(int capacity) { + return (T[]) new Object[capacity]; + } +}