From e6561c5ed6cb6fcb81ba459eee7b14002e4dee35 Mon Sep 17 00:00:00 2001 From: Anton Date: Fri, 23 Mar 2018 00:02:24 +0300 Subject: [PATCH 1/3] =?UTF-8?q?=D0=97=D0=B0=D0=B4=D0=B0=D0=BD=D0=B8=D0=B5?= =?UTF-8?q?=202.?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- hw_02/pom.xml | 27 +++++ hw_02/src/main/java/hw_02/DictImpl.java | 127 ++++++++++++++++++++++ hw_02/src/main/java/hw_02/Dictionary.java | 31 ++++++ hw_02/src/test/java/hw_02/DictTest.java | 78 +++++++++++++ 4 files changed, 263 insertions(+) create mode 100644 hw_02/pom.xml create mode 100644 hw_02/src/main/java/hw_02/DictImpl.java create mode 100644 hw_02/src/main/java/hw_02/Dictionary.java create mode 100644 hw_02/src/test/java/hw_02/DictTest.java diff --git a/hw_02/pom.xml b/hw_02/pom.xml new file mode 100644 index 0000000..9a1e742 --- /dev/null +++ b/hw_02/pom.xml @@ -0,0 +1,27 @@ + + 4.0.0 + + 2 + hw_02 + 0.0.1-SNAPSHOT + jar + + hw_02 + http://maven.apache.org + + + UTF-8 + 1.8 + 1.8 + + + + + junit + junit + 3.8.1 + test + + + diff --git a/hw_02/src/main/java/hw_02/DictImpl.java b/hw_02/src/main/java/hw_02/DictImpl.java new file mode 100644 index 0000000..98346f5 --- /dev/null +++ b/hw_02/src/main/java/hw_02/DictImpl.java @@ -0,0 +1,127 @@ +package hw_02; + +public class DictImpl implements Dictionary { + private Node[] arr; + int arrSize; + double maxLoadFactor = 0.75; + private double minLoadFactor = 0.2; + private final int minSize = 4; + private int size = 0; + + public void clear() { + size = 0; + arrSize = minSize; + resetArray(); + } + + private void resetArray() { + arr = new Node[arrSize]; + for (int i = 0; i < arrSize; i++) { + arr[i] = new Node(); + } + } + + public DictImpl() { + clear(); + } + + public DictImpl(double maxLoadFactor) { + this(); + this.minLoadFactor = maxLoadFactor / 3; + this.maxLoadFactor = maxLoadFactor; + } + + public int size() { + return size; + } + + public boolean contains(String key) { + return lookup(key).next != null; + } + + public String get(String key) { + Node p = lookup(key).next; + if (p == null) { + return null; + } + return p.value; + } + + public String put(String key, String value) { + Node p = lookup(key); + String oldValue = null; + if (p.next != null) { + oldValue = p.next.value; + p.next.value = value; + } else { + p.next = new Node(key, value); + size++; + } + rehashIfNeeded(); + return oldValue; + } + + public String remove(String key) { + Node p = lookup(key); + String oldValue = null; + if (p.next != null) { + oldValue = p.next.value; + p.next = p.next.next; + size--; + } + rehashIfNeeded(); + return oldValue; + } + + private Node lookup(String s) { + Node p = arr[arrIdx(s)]; + + while (p.next != null && !p.next.key.equals(s)) { + p = p.next; + } + + return p; + } + + private int arrIdx(String s) { + return s.hashCode() % arrSize; + } + + private void rehashIfNeeded() { + if (size > arrSize * maxLoadFactor) { + arrSize *= 2; + } else if (size < arrSize * minLoadFactor) { + if (arrSize >= 2 * minSize) { + arrSize /= 2; + } + } else { + return; + } + + Node[] oldArr = arr; + + resetArray(); + + for (int i = 0; i < oldArr.length; i++) { + Node p = oldArr[i].next; + while (p != null) { + Node q = p; + p = p.next; + + int currIdx = arrIdx(q.key); + q.next = arr[currIdx].next; + arr[currIdx].next = q; + } + } + } + + private class Node { + public Node(String key2, String value2) { + key = key2; + value = value2; + } + public Node() {} + String key, value; + Node next; + } +} diff --git a/hw_02/src/main/java/hw_02/Dictionary.java b/hw_02/src/main/java/hw_02/Dictionary.java new file mode 100644 index 0000000..60b00b7 --- /dev/null +++ b/hw_02/src/main/java/hw_02/Dictionary.java @@ -0,0 +1,31 @@ +package hw_02; + +public interface Dictionary { + + // хеш-таблица, использующая список + // ключами и значениями выступают строки + // стандартный способ получить хеш объекта -- вызвать у него метод hashCode() + + // кол-во ключей в таблице + int size(); + + // true, если такой ключ содержится в таблице + boolean contains(String key); + + // возвращает значение, хранимое по ключу key + // если такого нет, возвращает null + String get(String key); + + // положить по ключу key значение value + // и вернуть ранее хранимое, либо null; + // провести рехеширование по необходимости + String put(String key, String value); + + // забыть про пару key-value для переданного key + // и вернуть забытое value, либо null, если такой пары не было; + // провести рехеширование по необходимости + String remove(String key); + + // забыть про все пары key-value + void clear(); +} diff --git a/hw_02/src/test/java/hw_02/DictTest.java b/hw_02/src/test/java/hw_02/DictTest.java new file mode 100644 index 0000000..296c150 --- /dev/null +++ b/hw_02/src/test/java/hw_02/DictTest.java @@ -0,0 +1,78 @@ +package hw_02; + +import junit.framework.TestCase; + +public class DictTest extends TestCase { + + private DictImpl d; + + public void setUp() { + d = new DictImpl(); + } + + public void testPutContains() { + assertEquals(0, d.size()); + assertFalse(d.contains("a")); + assertEquals(null, d.put("a", "a1")); + assertEquals("a1", d.put("a", "a2")); + assertEquals(1, d.size()); + } + + public void testGet() { + assertEquals(null, d.get("a")); + d.put("a", "a1"); + d.put("b", "b1"); + assertEquals("a1", d.get("a")); + assertEquals("b1", d.get("b")); + assertEquals(2, d.size()); + } + + public void testRemove() { + assertEquals(null, d.remove("a")); + assertEquals(0, d.size()); + d.put("a", "a1"); + d.put("b", "b1"); + assertEquals("a1", d.remove("a")); + assertEquals(1, d.size()); + assertEquals("b1", d.remove("b")); + assertEquals(0, d.size()); + } + + public void testRehash() { + d.put("a", "a1"); + d.put("b", "b1"); + d.put("c", "c1"); + d.put("d", "d1"); + //после 4 элементов должен произойти rehash + assertEquals(4, d.size()); + assertEquals(8, d.arrSize); + assertEquals("a1", d.get("a")); + assertEquals("b1", d.get("b")); + assertEquals("c1", d.get("c")); + assertEquals("d1", d.get("d")); + } + + public void testList() { + d.arrSize = 1; + d.maxLoadFactor = 100; + + d.put("a", "a1"); + d.put("b", "b1"); + d.put("c", "c1"); + + assertEquals("a1", d.remove("a")); + assertEquals("b1", d.get("b")); + assertEquals("c1", d.remove("c")); + + assertEquals(1, d.size()); + } + + public void testClear() { + d.put("a", "a1"); + + d.clear(); + + assertEquals(0, d.size()); + assertEquals(null, d.get("a")); + } +} From af97d8d8e38a955dbc058b0f33f43bc8e894489b Mon Sep 17 00:00:00 2001 From: Anton Date: Fri, 23 Mar 2018 00:13:18 +0300 Subject: [PATCH 2/3] test --- hw_02/.project | 23 +++++++++++++++++++++++ 1 file changed, 23 insertions(+) create mode 100644 hw_02/.project diff --git a/hw_02/.project b/hw_02/.project new file mode 100644 index 0000000..ca69dda --- /dev/null +++ b/hw_02/.project @@ -0,0 +1,23 @@ + + + hw_02 + + + + + + org.eclipse.jdt.core.javabuilder + + + + + org.eclipse.m2e.core.maven2Builder + + + + + + org.eclipse.jdt.core.javanature + org.eclipse.m2e.core.maven2Nature + + From ca6d8d44d40daee61b3f30a8b53e3ce0de01903b Mon Sep 17 00:00:00 2001 From: Anton Date: Fri, 23 Mar 2018 00:16:55 +0300 Subject: [PATCH 3/3] delete --- hw_02/.project | 23 ----------------------- 1 file changed, 23 deletions(-) delete mode 100644 hw_02/.project diff --git a/hw_02/.project b/hw_02/.project deleted file mode 100644 index ca69dda..0000000 --- a/hw_02/.project +++ /dev/null @@ -1,23 +0,0 @@ - - - hw_02 - - - - - - org.eclipse.jdt.core.javabuilder - - - - - org.eclipse.m2e.core.maven2Builder - - - - - - org.eclipse.jdt.core.javanature - org.eclipse.m2e.core.maven2Nature - -