3

インデックスを使用してリストデータ構造をどのように反復しますか。たとえば、各要素が単語であるリスト形式の文を考えてみましょう。インデックスを使用して各単語をステップ実行できますか? このようなもの -

// sentence defined something like this - List<String>
int size = sentence.size();
for (int i=0; i<size-1; i++)
{
    System.out.println(sentence[i] + " " + sentence[i+1]);
}

もちろん、上記のコードは機能しませんが、それらの行で何かを行うことは可能ですか? ご覧のとおり、2 つの連続する要素にアクセスしたいのですが、イテレータを使用すると、非常に面倒になり始めます。

4

6 に答える 6

6

get(i)の代わりにメソッドを使用できます[i]

for (int i=0; i<size-1; i++) {
    System.out.println(sentence.get(i) + " " + sentence.get(i+1));
}
于 2012-09-08T23:52:09.587 に答える
5

Listインスタンスは配列と同じではありません。特定のインデックスでアイテムを取得するための特定の方法があります。これを試して:

// sentence defined something like this - List<String>
int size = sentence.size();
for (int i=0; i<size-1; i++)
{
    System.out.println(sentence.get(i) + " " + sentence.get(i + 1));
}

配列 (例: String[] sentence = new String[]{"hello", "there"}) があれば、それは正常に機能します。

補足として、Java には、配列とs の両方で使用できる for-each ループがあります。List

for (String s : sentence) {
    // do something
}

もちろん、ループの各反復で複数のインデックスで要素にアクセスしているため、これは使用できませんが、このようなものが存在することを知っておくことが重要です。

于 2012-09-08T23:53:34.443 に答える
2

Javaのx[i]式構文は、配列にのみ使用できます。他には何もありません。

他の回答が述べているように、インデックスを使用してJavaリストの要素をステップスルーする方法は、を使用することList.get(int)です。ただし、これを行うときに考慮する必要がある重要なパフォーマンスの問題があります。

問題は、get(int)呼び出しのコストが、List使用する実装クラスによって異なることです。

  • ArrayList(またはa Vector)の場合、get(int)長さNのリストに対する操作はですO(1)。つまり、リストの長さに依存せず、実際には安価です。。よりも少しだけ高価ですsomeArray[i]

  • の場合、リストLinkedListget(int)操作は、リストを最初から要求した位置に到達するまでステップスルーする必要があります。リストの長さがNの場合、(リスト内のランダムな位置を想定した)の平均コストは;です。つまり、リストの長さに比例します。長さが長い場合、それは高価になります。get(int)O(N)

対照的に、Iterator(明示的に、またはfor (E e : l)構文を使用して暗黙的に)を使用する場合、各要素の取得は、および(激しい競合などのマルチスレッドの問題を無視して)O(1)のすべてのリスト実装に対して行われます。java.utiljava.util.concurrent

そうは言っても、イテレータが機能せず、アプリケーションがインデックスを使用する必要がある場合があります。

于 2012-09-09T01:03:19.673 に答える
0

インデックスを使用せずに、リストから値の連続するペアを処理できます。1 つの方法を次に示します。

private void processWordsInSentence(List<String> sentence) {
    Iterator<String> it = sentence.iterator();
    if (it.hasNext()) {
        String previous = it.next();
        while(it.hasNext()) {
            String current = it.next();

            // use previous and current values, e.g.
            System.out.println(previous + " " + current);

            previous = current;
        }
    }
}

の代わりにこのようなものを使用したいのはなぜsentence.get(index)ですか? 私はいくつかの理由を提供します:

  1. あなたのサンプルでは、​​処理はリストからの連続した値に関係しており、それらの位置ではありません。したがって、インデックスを明示的にいじる必要があることに「付加価値」はありません。

  2. List<T>これは、複数の実装を持つインターフェイスであることを忘れないでください。は一定時間で実行されますが、同じ a の呼び出しにArrayList<T>はの値に比例する時間が必要です。したがって、実際のパフォーマンスに関する考慮事項がある可能性があります。.get(index)LinkedList<T>index

上記のprocessWordsInSentence実装では、要素が 2 つ未満のリストの場合を明示的に処理する必要があります。ガーディング内のループifはステートメントで記述できfor、トラバーサルを実際のデータの処理から分離することができます (そのスタイルを好む場合)。

private void processWordsInSentence(List<String> sentence) {
    Iterator<String> it = sentence.iterator();
    if (it.hasNext()) {
        for (
            String previous = it.next(), current = null;
            it.hasNext();
            previous = current
        ) {                
            // use previous and current values, e.g.
            System.out.println(previous + " " + current);
        }
    }
}
于 2012-09-09T00:40:12.940 に答える
0

この場合、例として Iterator を使用することもできます。

まず、ur 要素を arraylist に配置し、次のように Iterator を使用してみてください。

ArrayList arrayList = new ArrayList();

Iterator itr = arrayList.iterator();

while(itr.hasNext())
{
  System.out.println(itr.next()); // Print out the elements from arraylist

}
于 2012-09-09T00:00:02.473 に答える