web-dev-qa-db-ja.com

最後のforeachループの繰り返しを検出する

次のようなforeachループがあると仮定します。

Set<String> names = new HashSet<>();

//some code

for (String name: names) {

     //some code

}

foreachの内部で、実際の名前がSetの最後の名前であることをカウンターなしで確認する方法はありますか?

(質問が重複している場合は申し訳ありませんが、このような質問はここでは見つかりませんでした)

26
mhery

ありません。 Java 'for each'ループはどのように機能しますか?

イテレータを明示的に使用するか、intカウンタを使用するには、ループを変更する必要があります。

15
Lazar Petrovic

シンプルでわかりやすくするために、imoは次のことを行います。

Set<String> names = new HashSet<>();
Iterator<String> iterator = names.iterator();
    while (iterator.hasNext()) {
        String name = iterator.next();
        //Do stuff
        if (!iterator.hasNext()) {
            //last name 
        }
     }

また、何を達成しようとしているかにもよります。各名前をコマで区切る一般的なユースケースを実装しているが、最後に空のコマを追加しないとしましょう:

Set<String> names = new HashSet<>();
names.add("Joao");
names.add("Pereira");

//if the result should be Joao, Pereira then something like this may work
String result = names.stream().collect(Collectors.joining(", "));
20
Joao Pereira

特定の質問に対してこのソリューションを追加するだけで、他の回答も完全に適切です。

Set<String> names = new HashSet<>();

   //some code
   int i = 0;

for (String name: names) {
    if(i++ == names.size() - 1){
        // Last iteration
    }
   //some code

}
11
Edu G

HashSetには既にString値が含まれているため、上記の答えの.map(String :: toString)は冗長です。順序が保証されないため、Setを使用して文字列を連結しないでください。

List<String> nameList = Arrays.asList("Michael", "Kate", "Tom");
String result = nameList.stream().collect(Collectors.joining(", "));
0
luk4

単純なリスト/セットだけでなく、複雑なオブジェクトを使用している場合は、次のコードが役立ちます。収集する前に、実際に目的の文字列を取得するマップ関数を追加するだけです。

String result = violations.stream().map(e->e.getMessage()).collect(Collectors.joining(", "));
0
Manoj G

現在の要素が最後の要素でもあるかどうかを確認するための組み込みメソッドはありません。それに加えて、戻り順序を保証しないHashSetを使用しています。確認したい場合でもインデックスiを使用すると、最後の要素は常に別の要素になる可能性があります。

0
Murat Karagöz

Setは、その中のアイテムの順序を保証しません。 Setを1回ループして「abc」を「最後のアイテム」として取得し、次に「hij」がSetの「最後のアイテム」であることがわかります。

そうは言っても、順序を気にせず、その瞬間にSetを観察するときに任意の「最後の項目」が何であるかを知りたいだけの場合、これを行う方法はありません。カウンターを使用する必要があります。

0
CraigR8806