Ölçütlerle eşleşen ilk öğeyi getir


122

Bir akıştaki bir ölçütle eşleşen ilk öğe nasıl elde edilir? Bunu denedim ama çalışmıyor

this.stops.stream().filter(Stop s-> s.getStation().getName().equals(name));

Bu ölçüt çalışmıyor, filtre yöntemi Stop dışındaki bir sınıfta çağrılıyor.

public class Train {

private final String name;
private final SortedSet<Stop> stops;

public Train(String name) {
    this.name = name;
    this.stops = new TreeSet<Stop>();
}

public void addStop(Stop stop) {
    this.stops.add(stop);
}

public Stop getFirstStation() {
    return this.getStops().first();
}

public Stop getLastStation() {
    return this.getStops().last();
}

public SortedSet<Stop> getStops() {
    return stops;
}

public SortedSet<Stop> getStopsAfter(String name) {


    // return this.stops.subSet(, toElement);
    return null;
}
}


import java.util.ArrayList;
import java.util.List;

public class Station {
private final String name;
private final List<Stop> stops;

public Station(String name) {
    this.name = name;
    this.stops = new ArrayList<Stop>();

}

public String getName() {
    return name;
}

}

Yanıtlar:


215

Aradığınız şey bu olabilir:

yourStream
    .filter(/* your criteria */)
    .findFirst()
    .get();



Bir örnek:

public static void main(String[] args) {
    class Stop {
        private final String stationName;
        private final int    passengerCount;

        Stop(final String stationName, final int passengerCount) {
            this.stationName    = stationName;
            this.passengerCount = passengerCount;
        }
    }

    List<Stop> stops = new LinkedList<>();

    stops.add(new Stop("Station1", 250));
    stops.add(new Stop("Station2", 275));
    stops.add(new Stop("Station3", 390));
    stops.add(new Stop("Station2", 210));
    stops.add(new Stop("Station1", 190));

    Stop firstStopAtStation1 = stops.stream()
            .filter(e -> e.stationName.equals("Station1"))
            .findFirst()
            .get();

    System.out.printf("At the first stop at Station1 there were %d passengers in the train.", firstStopAtStation1.passengerCount);
}

Çıktı:

At the first stop at Station1 there were 250 passengers in the train.

Bana Criteria için bir örnek verebilir misiniz lütfen? (Stop s: listofstops) {if (s.name.equals ("Linz") return r}
user2147674

1
Duraklar başka bir sınıftır, yöntem filtresi Train'de istila edilir, ancak SortedSet duraklarının tüm Durdurma öğelerinde gezinmek istiyorum
user2147674

2
Yanlış olduğum ortaya çıktı - tembel akışlar verimsizliği
önlüyor

2
@alexpfx kullanabilirsiniz .findFirst().orElse(yourBackUpGoesHere);. Bu da boş olabilir .findFirst().orElse(null);
ifloop

1
@iammrmehul No. , boş olabilecek findFirst()bir İsteğe Bağlı nesne ( JavaDoc ) döndürür . Bu durumda, çağrı get()NPE'yi atacaktır. Bunun olmasını önlemek için, orElse()yerine get()bir geri dönüş nesnesi (gibi orElse(new Station("dummy", -1)) kullanın ve sağlayın veya sonucunu findFirst()bir değişkende saklayın ve isEmpty()aramadan önce kontrol edinget()
ifloop

7

Bir lambda ifadesi yazdığınızda, solundaki ->argüman listesi parantezli bir argüman listesi (muhtemelen boş) veya parantez içermeyen tek bir tanımlayıcı olabilir . Ancak ikinci biçimde, tanımlayıcı bir tür adıyla bildirilemez. Böylece:

this.stops.stream().filter(Stop s-> s.getStation().getName().equals(name));

yanlış sözdizimidir; fakat

this.stops.stream().filter((Stop s)-> s.getStation().getName().equals(name));

doğru. Veya:

this.stops.stream().filter(s -> s.getStation().getName().equals(name));

derleyici türleri bulmak için yeterli bilgiye sahipse de doğrudur.


İkincisi ile, "yerel değişkenler oluştur" mesajı
alıyorum

@ user2147674 Bu bir hata mesajı mı? Yoksa derleyici s, lambda ile kullanmak için yeni bir "yerel değişken" türü yarattığını size mi bildiriyor? Bana gerçekten bir hata gibi görünmüyor, ama görünüşe göre seninle aynı derleyiciyi kullanmıyorum.
ajb

1
@ user2147674 Bu oldukça garip. İkinci örneği kullanabiliyorum ( findFirst().get()sonrasına uygulandı filter) ve herhangi bir hata almıyorum. Üçüncü örnek de benim için çalışıyor.
ajb

3

Bunun en iyi yol olduğunu düşünüyorum:

this.stops.stream().filter(s -> Objects.equals(s.getStation().getName(), this.name)).findFirst().orElse(null);
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.