4114

JavaのaHashMapとaの違いは何ですか?Hashtable

スレッド化されていないアプリケーションでは、どちらがより効率的ですか?

4

35 に答える 35

4079

HashMapHashtableJava にはいくつかの違いがあります。

  1. Hashtable同期されていますが、HashMapそうではありません。HashMap同期されていないオブジェクトは通常、同期されているオブジェクトよりもパフォーマンスが優れているため、これはスレッド化されていないアプリケーションに適しています。

  2. Hashtablenullキーまたは値 を許可しません。HashMap1 つのnullキーと任意の数のnull値を使用できます。

  3. HashMap のサブクラスの 1 つがであるため、予測可能な反復順序 (デフォルトでは挿入順序) が必要な場合は、をLinkedHashMapと簡単に交換できます。を使用している場合、これはそれほど簡単ではありません。HashMapLinkedHashMapHashtable

同期は問題にならないので、 をお勧めしHashMapます。同期が問題になる場合は、 も参照してくださいConcurrentHashMap

于 2008-09-02T23:02:37.180 に答える
754

回答の多くは、Hashtable が同期されていると述べていることに注意してください。 実際には、これで得られるものはほとんどありません。 同期はアクセサー/ミューテーター メソッドで行われ、2 つのスレッドが同時にマップに追加またはマップから削除するのを停止しますが、実際には追加の同期が必要になることがよくあります。

非常に一般的なイディオムは、"check then put" です。つまり、 内のエントリを探し、Mapまだ存在しない場合は追加します。Hashtableこれは、またはを使用するかどうかにかかわらず、決してアトミック操作ではありませんHashMap

同等の同期は、次のHashMap方法で取得できます。

Collections.synchronizedMap(myMap);

ただし、このロジックを正しく実装するには、フォームの追加の同期が必要です。

synchronized(myMap) {
    if (!myMap.containsKey("tomato"))
        myMap.put("tomato", "red");
}

Hashtableのエントリ (またはHashMapによって取得された) を反復処理しても、追加の同期によって が変更されCollections.synchronizedMapないように保護しない限り、スレッドセーフではありません。Map

ConcurrentMapインターフェースの実装(例: ) は、次のようなスレッド セーフな check-then-act セマンティクスConcurrentHashMapを含めることで、この問題の一部を解決します。

ConcurrentMap.putIfAbsent(key, value);
于 2008-09-03T11:00:41.213 に答える
214

この質問は、候補者がコレクションクラスの正しい使用法を理解しており、利用可能な代替ソリューションを認識しているかどうかを確認するために、面接でよく尋ねられます。

  1. このHashMapクラスはHashtable、同期されておらず、nullを許可することを除いて、とほぼ同じです。(HashMapキーと値としてnull値を許可しますが、sHashtableは許可しませんnull)。
  2. HashMapマップの順序が時間の経過とともに一定に保たれることを保証するものではありません。
  3. HashMap同期されているのに対し、Hashtableは同期されていません。
  4. のイテレータHashMapはフェイルセーフですが、の列挙子はフェイルセーフではなく、他のスレッドが独自の メソッド以外の要素を追加または削除してマップを構造的に変更した場合Hashtableにスローされます。ただし、これは保証された動作ではなく、JVMが最善を尽くして実行します。ConcurrentModificationExceptionIteratorremove()

いくつかの重要な用語に関する注意:

  1. 同期とは、ある時点で1つのスレッドのみがハッシュテーブルを変更できることを意味します。基本的に、これは、で更新を実行する前のスレッドHashtableはオブジェクトのロックを取得する必要があり、他のスレッドはロックが解放されるのを待つことを意味します。
  2. フェイルセーフは、イテレータのコンテキスト内で関連しています。コレクションオブジェクトにイテレータが作成されていて、他のスレッドがコレクションオブジェクトを「構造的に」変更しようとすると、同時変更例外がスローされます。setコレクションを「構造的に」変更しないため、他のスレッドがメソッドを呼び出すことは可能です。ただし、を呼び出す前にset、コレクションが構造的に変更されている場合IllegalArgumentExceptionは、スローされます。
  3. 構造変更とは、マップの構造を効果的に変更できる要素を削除または挿入することを意味します。

HashMapによって同期することができます

Map m = Collections.synchronizeMap(hashMap);

Mapは、列挙オブジェクトを介した反復の直接サポートではなく、コレクションビューを提供します。このセクションで後述するように、コレクションビューはインターフェイスの表現力を大幅に向上させます。マップを使用すると、キー、値、またはキーと値のペアを反復処理できます。Hashtable3番目のオプションは提供しません。マップは、反復の最中にエントリを削除する安全な方法を提供します。Hashtableしませんでした。最後に、Mapはインターフェースの小さな欠陥を修正しHashtableます。Hashtablecontainsが指定された値を含む場合、trueを返すcontainsというメソッドがありHashtableます。その名前をHashtable指定すると、キーがのプライマリアクセスメカニズムであるため、指定されたキーが含まれている場合、このメソッドがtrueを返すことが期待されますHashtable。マップインターフェイスは、メソッドの名前を変更することにより、この混乱の原因を排除しますcontainsValue。また、これにより、インターフェイスの一貫性が向上します—containsValueパラレルcontainsKey

マップインターフェイス

于 2011-10-04T06:39:52.813 に答える
146

HashMap:Mapハッシュ コードを使用して配列にインデックスを付けるインターフェイスの実装。 Hashtable: こんにちは、1998 から電話がありました。彼らは、コレクション API を元に戻したいと考えています。

Hashtable真剣に、あなたは完全に離れた方が良いです. シングルスレッド アプリの場合、同期の余分なオーバーヘッドは必要ありません。並行性の高いアプリの場合、偏執的な同期により、飢餓、デッドロック、または不要なガベージ コレクションの一時停止が発生する可能性があります。Tim Howland が指摘したように、ConcurrentHashMap代わりに使用できます。

于 2008-09-02T23:14:11.333 に答える
140

は、HashTableJava Collections Framework (JCF) が導入される前はレガシー クラスであり、後でMapインターフェースを実装するために改良されたことに注意してください。VectorともそうだったStack

したがって、他の人が指摘したように、JCFには常により良い代替手段があるため、新しいコードでは常にそれらに近づかないでください。

これは、役に立つJava コレクションのチート シートです。灰色のブロックには、従来のクラス HashTable、Vector、および Stack が含まれていることに注意してください。

ここに画像の説明を入力

于 2014-03-25T08:58:01.233 に答える
71

このチャートを見てください。HashMapおよびとともに、異なるデータ構造間の比較を提供しますHashtable。比較は正確で、明確で、理解しやすいです。

Java コレクション マトリックス

于 2012-11-20T05:35:53.423 に答える
70

izbが言ったことに加えて、HashMapnull値を許可しますが、は許可Hashtableしません。

また、 Javadocsの状態として廃止され、インターフェースに置き換えられたクラスをHashtable拡張することにも注意してください。DictionaryMap

于 2008-09-02T20:30:00.200 に答える
53

Hashtableに似てHashMapおり、同様のインターフェイスを備えています。メソッドは同期HashMapされているため、レガシーアプリケーションのサポートが必要な場合や同期が必要な場合を除いて、を使用することをお勧めします。Hashtablesしたがって、マルチスレッドではない場合HashMapsは、最善の策です。

于 2008-09-02T20:25:30.117 に答える
45

Hashtable同期されていますが、HashMapそうではありません。それはHashtableより遅くなりHashmapます。

シングル スレッド アプリケーションのHashMap場合は、それ以外の点では機能が同じであるため、使用します。

于 2008-09-02T20:22:34.023 に答える
39

ここで既に述べた他のすべての重要な側面に加えて、コレクション API (Map インターフェースなど) は、Java 仕様への「最新かつ最高の」追加に準拠するために常に変更されています。

たとえば、Java 5 Map の反復を比較します。

for (Elem elem : map.keys()) {
  elem.doSth();
}

対古い Hashtable アプローチ:

for (Enumeration en = htable.keys(); en.hasMoreElements(); ) {
  Elem elem = (Elem) en.nextElement();
  elem.doSth();
}

Java 1.8 では、古き良きスクリプト言語のように HashMap を構築してアクセスできることも約束されています。

Map<String,Integer> map = { "orange" : 12, "apples" : 15 };
map["apples"];

更新:いいえ、1.8 には実装されません... :(

Project Coin のコレクションの機能強化は JDK8 に含まれますか?

于 2012-01-12T09:17:16.543 に答える
39

hashtable と hashmap のもう 1 つの重要な違いは、HashMap の Iterator はフェイルファストであるのに対し、Hashtable の列挙子はそうではなく、他のスレッドが Iterator 自身の remove() メソッド以外の要素を追加または削除してマップを構造的に変更した場合に ConcurrentModificationException をスローすることです。しかし、これは保証された動作ではなく、ベスト エフォートで JVM によって実行されます。」

私の情報源: http://javarevisited.blogspot.com/2010/10/difference-between-hashmap-and.html

于 2011-09-08T06:40:13.040 に答える
32
  • HashTableは同期されます。単一のスレッドで使用している場合は、非同期バージョンであるHashMapを使用できます。同期されていないオブジェクトは、多くの場合、パフォーマンスが少し高くなります。ちなみに、複数のスレッドが同時に HashMap にアクセスし、そのうちの少なくとも 1 つのスレッドがマップを構造的に変更する場合は、外部で同期する必要があります。以下を使用して、同期されていないマップを同期されたマップにラップできます。

    Map m = Collections.synchronizedMap(new HashMap(...));
    
  • HashTable には、null 以外のオブジェクトのみをキーまたは値として含めることができます。HashMap には、1 つの null キーと null 値を含めることができます。

  • Map によって返されるイテレータはフェイルファストです。イテレータが作成された後、イテレータ自体の remove メソッド以外の方法でマップが構造的に変更された場合、イテレータはConcurrentModificationException. したがって、同時変更に直面した場合、反復子は、将来の不確定な時点で恣意的で非決定論的な動作を危険にさらすのではなく、迅速かつ明確に失敗します。一方、Hashtable のキーと要素のメソッドによって返される列挙はフェイル ファストではありません。

  • HashTable と HashMap はJava Collections Frameworkのメンバーです(Java 2 プラットフォーム v1.2 以降、HashTable は Map インターフェースを実装するように改良されました)。

  • HashTable はレガシー コードと見なされます。ドキュメントでは、スレッドセーフな高度な並行実装が必要な場合は、Hashtable の代わりにConcurrentHashMapを使用することをお勧めします。

  • HashMap は、要素が返される順序を保証しません。HashTable の場合も同じだと思いますが、完全にはわかりません。それを明確に述べているリソースが見つかりません。

于 2012-04-29T13:57:46.600 に答える
32

HashMapHashtableまた、アルゴリズムにも大きな違いがあります。これまで誰も言及していなかったので、私はそれを取り上げています。HashMap2 のべき乗サイズのハッシュ テーブルを構築し、それを動的に増やして、任意のバケットに最大で約 8 つの要素 (衝突) があり、一般的な要素タイプの要素を非常にうまく攪拌します。ただし、Hashtable何をしているのかを知っている場合、実装はハッシュをより細かく制御します。つまり、値のドメインサイズに最も近い素数などを使用してテーブルサイズを修正できます。これにより、HashMap よりもパフォーマンスが向上します。つまり、衝突が少なくなります。場合によっては。

この質問で広く議論されている明らかな違いとは別に、Hashtable はハッシュをより適切に制御できる「手動駆動」の車であり、HashMap は一般的にうまく機能する「自動駆動」の対応物であると考えています。

于 2012-12-10T08:57:14.940 に答える
31

ここの情報に基づいて、HashMap を使用することをお勧めします。最大の利点は、イテレータを使用しない限り、Java が反復処理中に変更できないことだと思います。

于 2008-09-02T20:14:53.840 に答える
19

スレッド化されたアプリの場合、パフォーマンス要件に応じて、ConcurrentHashMapを使用しないことがよくあります。

于 2008-09-02T22:38:59.843 に答える
13

HashMap: java.util パッケージ内で使用可能なクラスであり、要素をキーと値の形式で格納するために使用されます。

Hashtable: コレクション フレームワーク内で認識されている従来のクラスです。

于 2013-01-31T13:41:05.737 に答える
13

私の小さな貢献:

  1. まず、 と の最も重要な違いはHashtable、がスレッドセーフなコレクションであるのに対し、 はスレッドセーフではないHashMapということです。HashMapHashtable

  2. Hashtableとの 2 番目の重要な違いHashMapはパフォーマンスです。HashMapは同期されていないため、 よりもパフォーマンスが優れていHashtableます。

  3. Hashtablevsの 3 番目の違いHashMapは、廃止されたクラスであり、Javaの代わりにHashtable使用する必要があることです。ConcurrentHashMapHashtable

于 2014-03-18T21:46:56.690 に答える
12
  1. Hashtable同期されていますが、HashMapそうではありません。
  2. もう 1 つの違いは、 のイテレータHashMapがフェールセーフであるのに対し、 の列挙子はそうでHashtableはないことです。反復中にマップを変更すると、わかります。
  3. HashMapnull 値を許可しますが、許可しHashtableません。
于 2013-01-22T05:31:19.947 に答える
10

HashTableは、jdk のレガシー クラスであり、今後は使用しないでください。その使用法をConcurrentHashMapに置き換えます。スレッドセーフが必要ない場合は、スレッドセーフではありませんが高速でメモリ使用量が少ないHashMapを使用してください。

于 2013-04-15T14:49:52.357 に答える
10

ハッシュマップとハッシュテーブル

  • HashMap と HashTable に関するいくつかの重要なポイント。以下の詳細をお読みください。

1) Hashtable と Hashmap は java.util.Map インターフェイスを実装します。 2) Hashmap と Hashtable はどちらもハッシュ ベースのコレクションです。ハッシュに取り組んでいます。これらは HashMap と HashTable の類似点です。

  • HashMap と HashTable の違いは何ですか?

1) 最初の違いは、HashMap はスレッド セーフではありませんが、HashTable は ThreadSafe です
。2) HashMap はスレッド セーフではないため、パフォーマンスが優れています。一方、Hashtable のパフォーマンスはスレッドセーフであるため、それほど優れていません。そのため、複数のスレッドが同時に Hashtable にアクセスすることはできません。

于 2014-07-05T06:27:57.807 に答える
9

Hashtable:

ハッシュテーブルは、キーと値のペアの値を保持するデータ構造です。キーと値の両方に null を許可しません。NullPointerExceptionnull 値を追加すると、 が得られます。同期されています。したがって、それにはコストがかかります。特定の時点でHashTableにアクセスできるスレッドは 1 つだけです。

import java.util.Map;
import java.util.Hashtable;

public class TestClass {

    public static void main(String args[ ]) {
    Map<Integer,String> states= new Hashtable<Integer,String>();
    states.put(1, "INDIA");
    states.put(2, "USA");

    states.put(3, null);    //will throw NullPointerEcxeption at runtime

    System.out.println(states.get(1));
    System.out.println(states.get(2));
//  System.out.println(states.get(3));

    }
}

ハッシュマップ:

HashMapHashtableに似ていますが、キーと値のペアも受け入れます。キーと値の両方に null を許可します。そのパフォーマンスは よりも優れHashTableていunsynchronizedます。

例:

import java.util.HashMap;
import java.util.Map;

public class TestClass {

    public static void main(String args[ ]) {
    Map<Integer,String> states = new HashMap<Integer,String>();
    states.put(1, "INDIA");
    states.put(2, "USA");

    states.put(3, null);    // Okay
    states.put(null,"UK");

    System.out.println(states.get(1));
    System.out.println(states.get(2));
    System.out.println(states.get(3));

    }
}
于 2015-02-10T07:44:31.213 に答える
6

Java の Hashtable は、Map Interface の存在により廃止された Dictionary クラスのサブクラスであるため、使用されなくなりました。さらに、Hashtable で実行できる Map インターフェイスを実装するクラスで実行できないことはありません。

于 2014-03-07T15:02:41.567 に答える
6

同期またはスレッドセーフ:

ハッシュマップは同期されていないため、スレッドセーフではなく、適切な同期ブロックがないと複数のスレッド間で共有できませんが、ハッシュテーブルは同期されているためスレッドセーフです。

null キーと null 値:

HashMap では、1 つの null キーと任意の数の null 値を使用できます。Hashtable では、null キーまたは null 値を使用できません。

値の反復:

HashMap の Iterator はフェイルファスト イテレーターですが、Hashtable の列挙子はそうではなく、他のスレッドが Iterator 自身の remove() メソッド以外の要素を追加または削除してマップを構造的に変更した場合、ConcurrentModificationException をスローします。

スーパークラスとレガシー:

HashMap は AbstractMap クラスのサブクラスですが、Hashtable は Dictionary クラスのサブクラスです。

パフォーマンス:

HashMap は同期されないため、Hashtable と比較して高速です。

Java コレクションに関連する例とインタビューの質問とクイズについては、http://modernpathshala.com/Article/1020/difference-between-hashmap-and-hashtable-in-javaを参照してください。

于 2016-01-05T18:35:42.627 に答える
6

古くて古典的なトピックですが、これを説明するこの役立つブログを追加したいだけです:

http://blog.manishchhabra.com/2012/08/the-5-main-differences-betwen-hashmap-and-hashtable/

Manish Chhabra のブログ

HashMap と Hashtable の 5 つの主な違い

HashMap と Hashtable はどちらも java.util.Map インターフェースを実装していますが、Java 開発者がより効率的なコードを作成するために理解する必要があるいくつかの違いがあります。Java 2 プラットフォーム v1.2 では、Hashtable クラスが改良されて Map インターフェースが実装され、Java Collections Framework のメンバーになりました。

  1. HashMap と Hashtable の主な違いの 1 つは、HashMap が非同期であるのに対し、Hashtable は同期されていることです。つまり、Hashtable はスレッドセーフで複数のスレッド間で共有できますが、HashMap は適切な同期なしでは複数のスレッド間で共有できません。Java 5 では、Hashtable の代替であり、Java の Hashtable よりも優れたスケーラビリティを提供する ConcurrentHashMap が導入されました。Synchronized は、ある時点で 1 つのスレッドのみがハッシュ テーブルを変更できることを意味します。基本的に、ハッシュテーブルの更新を実行する前にスレッドがオブジェクトのロックを取得する必要があることを意味し、他のスレッドはロックが解放されるのを待ちます。

  2. HashMap クラスは、null を許可することを除いて、Hashtable とほぼ同じです。(HashMap は null 値をキーと値として許可しますが、Hashtable は null を許可しません)。

  3. HashMap と Hashtable の 3 番目の重要な違いは、HashMap の Iterator はフェイルファスト イテレーターであるのに対し、Hashtable の列挙子はフェイルファスト イテレーターではなく、他のスレッドがイテレーター自身の remove( ) 方法。ただし、これは保証された動作ではなく、ベスト エフォートで JVM によって実行されます。これは、Java における Enumeration と Iterator の重要な違いでもあります。

  4. Hashtable と HashMap のもう 1 つの注目すべき違いは、シングル スレッド環境で使用する場合、スレッド セーフと同期のため、Hashtable は HashMap よりもはるかに遅いことです。したがって、同期が必要なく、HashMap が 1 つのスレッドでのみ使用される場合は、Java で Hashtable を実行します。

  5. HashMap は、マップの順序が時間の経過とともに一定に保たれることを保証しません。

HashMap は次の方法で同期できることに注意してください。

Map m = Collections.synchronizedMap(hashMap);

要約すると、Java の Hashtable と HashMap にはスレッドセーフと速度などの大きな違いがあり、これに基づいて、スレッドセーフが絶対に必要な場合にのみ Hashtable を使用します。Java 5 を実行している場合は、Java で ConcurrentHashMap を使用することを検討してください。

于 2014-08-17T09:58:38.813 に答える
3

HashMaps を使用すると、同期の自由が得られ、デバッグがはるかに簡単になります

于 2012-08-09T12:28:45.020 に答える
3

HashMap は、要素をキーと値の形式で格納するために使用されるクラスです。スレッドセーフではありません。同期されていないため.Hashtableが同期されているため.Hashmapはnullを許可しますが、hastableはnullを許可しません。

于 2013-07-23T15:50:26.577 に答える