Ich weiß, dass es in Java selbst kein direktes Äquivalent gibt, aber vielleicht einen Dritten?
Es ist wirklich praktisch. Derzeit möchte ich einen Iterator implementieren, der alle Knoten in einem Baum ergibt, dh etwa fünf Codezeilen mit Ausbeute.
java
yield
yield-return
ripper234
quelle
quelle
Antworten:
Die beiden mir bekannten Optionen sind die Infomancers-Collections-Bibliothek von Aviad Ben Dov aus dem Jahr 2007 und die YieldAdapter-Bibliothek von Jim Blackler aus dem Jahr 2008 (die auch in der anderen Antwort erwähnt wird).
Mit beiden können Sie Code mit einem
yield return
ähnlichen Konstrukt in Java schreiben , sodass beide Ihre Anforderung erfüllen. Die bemerkenswerten Unterschiede zwischen den beiden sind:Mechanik
Die Bibliothek von Aviad verwendet die Bytecode-Manipulation, während die von Jim Multithreading verwendet. Abhängig von Ihren Anforderungen kann jeder seine eigenen Vor- und Nachteile haben. Es ist wahrscheinlich, dass die Lösung von Aviad schneller ist, während die von Jim portabler ist (zum Beispiel glaube ich nicht, dass die Bibliothek von Aviad unter Android funktioniert).
Schnittstelle
Die Bibliothek von Aviad verfügt über eine übersichtlichere Benutzeroberfläche - hier ein Beispiel:
Während Jims viel komplizierter ist, müssen Sie
adept
ein Generikum verwenden,Collector
das einecollect(ResultHandler)
Methode hat ... ugh. Sie könnten jedoch so etwas wie diesen Wrapper um Jims Code von Zoom Information verwenden, was das erheblich vereinfacht:Lizenz
Die Lösung von Aviad ist BSD.
Jims Lösung ist gemeinfrei, ebenso wie der oben erwähnte Wrapper.
quelle
AbstractIterator
.yield(i)
ab JDK 13 nicht mehr funktioniert, dayield
es als neue Java-Anweisung / reserviertes Schlüsselwort hinzugefügt wird.Beide Ansätze können jetzt etwas sauberer gemacht werden, da Java Lambdas hat. Sie können so etwas tun
Ich habe hier etwas mehr erklärt.
quelle
Yielderable
? Sollte es nicht einfach so seinYieldable
? (Das Verb ist nur "Ausbeute", nicht "Ertrag" oder "Ertrag" oder was auch immer)yield -> { ... }
wird ab JDK 13 unterbrochen, dayield
es als neue Java-Anweisung / reserviertes Schlüsselwort hinzugefügt wird.Ich weiß, dass es hier eine sehr alte Frage ist, und es gibt zwei oben beschriebene Möglichkeiten:
yield
, das hat offensichtlich Ressourcenkosten.Es gibt jedoch eine andere, dritte und wahrscheinlich natürlichste Möglichkeit, den
yield
Generator in Java zu implementieren, die der Implementierung von C # 2.0+ -Compilern zuryield return/break
Generierung am nächsten kommt : lombok-pg . Es basiert vollständig auf einer Zustandsmaschine und erfordert eine enge Zusammenarbeitjavac
, um den Quellcode AST zu manipulieren. Leider scheint die lombok-pg-Unterstützung eingestellt zu sein (seit mehr als ein oder zwei Jahren keine Repository-Aktivität mehr), und dem ursprünglichen Projekt Lombok fehlt leider dieyield
Funktion (es hat jedoch eine bessere IDE wie Eclipse, IntelliJ IDEA-Unterstützung).quelle
Stream.iterate (seed, seedOperator) .limit (n) .foreach (action) ist nicht dasselbe wie Yield Operator, aber es kann nützlich sein, eigene Generatoren folgendermaßen zu schreiben:
quelle
Ich würde auch vorschlagen, wenn Sie RXJava bereits in Ihrem Projekt verwenden, um ein Observable als "Yielder" zu verwenden. Es kann auf ähnliche Weise verwendet werden, wenn Sie Ihr eigenes Observable erstellen.
Observables können in Iteratoren umgewandelt werden, sodass Sie sie sogar in traditionelleren for-Schleifen verwenden können. Auch RXJava bietet Ihnen wirklich leistungsstarke Tools, aber wenn Sie nur etwas Einfaches benötigen, wäre dies möglicherweise ein Overkill.
quelle
Ich habe hier gerade eine andere (MIT-lizenzierte) Lösung veröffentlicht , die den Produzenten in einem separaten Thread startet und eine begrenzte Warteschlange zwischen dem Produzenten und dem Konsumenten einrichtet , die Pufferung, Flusskontrolle und paralleles Pipelining zwischen Produzent und Konsument ermöglicht (so) dass der Verbraucher daran arbeiten kann, den vorherigen Artikel zu konsumieren, während der Produzent daran arbeitet, den nächsten Artikel zu produzieren).
Sie können dieses anonyme Formular für die innere Klasse verwenden:
beispielsweise:
Oder Sie können die Lambda-Notation verwenden, um die Boilerplate zu reduzieren:
quelle