Beim Durchlaufen der Konvertierung primitiver Arrays in Streams stellte ich fest, dass diese char[]nicht unterstützt werden, während andere primitive Array-Typen unterstützt werden. Gibt es einen besonderen Grund, sie im Stream auszulassen?
Beim Durchlaufen der Konvertierung primitiver Arrays in Streams stellte ich fest, dass diese char[]nicht unterstützt werden, während andere primitive Array-Typen unterstützt werden. Gibt es einen besonderen Grund, sie im Stream auszulassen?
Antworten:
Wie Eran sagte, ist es nicht der einzige, der fehlt.
A BooleanStreamwäre nutzlos, a ByteStream(falls vorhanden) kann als behandelt InputStreamoder in IntStream(wie möglich short) konvertiert und floatals DoubleStream.
Da charohnehin nicht alle Zeichen dargestellt werden können (siehe verlinkt), wäre es ein bisschen wie ein Legacy-Stream. Obwohl die meisten Leute sowieso nicht mit Codepunkten umgehen müssen, kann es seltsam erscheinen. Ich meine, Sie verwenden, String.charAt()ohne zu denken, "das funktioniert nicht in allen Fällen".
Einige Dinge wurden ausgelassen, weil sie nicht so wichtig waren. Wie von JB Nizet in der verknüpften Frage gesagt :
Die Designer haben sich ausdrücklich dafür entschieden, die Explosion von Klassen und Methoden zu vermeiden, indem sie die primitiven Streams auf drei Typen beschränkten, da die anderen Typen (char, short, float) durch ihr größeres Äquivalent (int, double) ohne signifikante Leistungseinbußen dargestellt werden können.
Der Grund BooleanStreamwäre nutzlos, weil Sie nur 2 Werte haben und dies die Operationen stark einschränkt. Es gibt keine mathematischen Operationen und wie oft arbeiten Sie überhaupt mit vielen booleschen Werten?
BooleanStreamwäre nutzlos": warum?
reduce(Boolean::logicalAnd)oder reduce(Boolean::logicalOr)auf einem boolean[]? Immerhin wurden die Methoden logicalAndund logicalOrin Java 8 hinzugefügt, damit ich diese Reduktionsoperationen von a ausführen kann. Stream<Boolean>Übrigens können Sie über eine char[]so einfache wie CharBuffer.wrap(array).chars()oder streamen CharBuffer.wrap(array).codePoints(), je nachdem, welche Semantik Sie bevorzugen.
Boolean::logicalAndexistiert, garantiert es nicht unbedingt die Existenz eines BooleanStream. Diese können schließlich in Lambda-Situationen ohne Strom verwendet werden. Ich kann mir vorstellen , dass jemand möchte zu tun reduce(Boolean::logicalAnd), aber in keinem Fall hat jemand Notwendigkeit , es zu tun.
while (i < limit), aber in keinem Fall hat jemand Notwendigkeit , es zu tun [über Zweig mit und Montageanleitung springen]“
<Primitive>Streamfür jeden primitiven Typ kein Nein gibt, ist, dass die API dadurch zu stark aufgebläht wird. Die richtige Frage lautet: "Warum gibt es IntStreamüberhaupt?" und die unglückliche Antwort ist, dass das Typensystem von Java nicht ausreichend ausgearbeitet ist, um es Stream<int>ohne den gesamten Leistungsaufwand der Verwendung auszudrücken Integer. Wenn Java Werttypen hätte, die auf dem Stapel zugewiesen oder direkt in andere Datenstrukturen eingebettet werden könnten, wäre nichts anderes erforderlichStream<T>
Die Antwort lautet natürlich " weil die Designer das entschieden haben ". Es gibt keinen technischen Grund, warum CharStreames nicht existieren könnte.
Wenn Sie eine Begründung wünschen, müssen Sie normalerweise die OpenJDK-Mailingliste * aktivieren. Die Dokumentation des JDK hat nicht die Gewohnheit zu rechtfertigen, warum irgendetwas der Grund ist, warum es ist.
Jemand fragte
Die Verwendung von IntStream zur Darstellung des Zeichen- / Byte-Streams ist etwas unpraktisch. Sollten wir auch CharStream und ByteStream hinzufügen?
Die Antwort von Brian Goetz (Java Language Architect) lautet
Kurze Antwort: nein.
Für diese Formulare, die fast nie verwendet werden, ist es nicht wert, jeweils mehr als 100.000 JDK-Footprint zu verwenden. Und wenn wir diese hinzufügen würden, würde jemand Short, Float oder Boolean verlangen.
Anders ausgedrückt, wenn die Leute darauf bestehen würden, dass wir alle primitiven Spezialisierungen haben, hätten wir keine primitiven Spezialisierungen. Welches wäre schlimmer als der Status Quo.
Das sagt er auch anderswo
Wenn Sie sie als Zeichen behandeln möchten, können Sie sie leicht genug auf Zeichen herabstufen. Scheint nicht wichtig genug zu sein, um eine ganze Reihe weiterer Streams zu haben. (Gleiches gilt für Short, Byte, Float).
TL; DR: Die Wartungskosten sind es nicht wert.
* Falls Sie neugierig sind, war die von mir verwendete Google-Abfrage
site:http://mail.openjdk.java.net/ charstream
100K+ of JDK footprint?
Es werden nicht nur charArrays nicht unterstützt.
Es gibt nur drei Arten von primitiven Strömen - IntStream, LongStreamundDoubleStream .
Als Ergebnis Arrayshat Methoden, die konvertieren int[], long[]unddouble[] in die entsprechenden primitiven Streams.
Es gibt keine entsprechenden Methoden für boolean[], byte[], short[], char[]und float[], da diese primitiven Typen haben keine primitive Strömen entsprechen.
charist ein abhängiger Teil von String- Speichern von UTF-16-Werten. Ein Unicode-Symbol, ein Codepunkt , ist manchmal ein Ersatzzeichenpaar. Daher deckt jede einfache Lösung mit Zeichen nur einen Teil der Unicode-Domäne ab.
Es gab eine Zeit, chardie ihr eigenes Recht hatte, ein öffentlicher Typ zu sein. Aber heutzutage ist es besser , verwenden Codepunkte ein IntStream. Ein Saiblingstrom konnte Ersatzpaare nicht einfach handhaben.
Der andere prosaischere Grund ist, dass das JVM- "Prozessor" -Modell ein intso kleinstes "Register" verwendet, dass Boolesche Werte, Bytes, Kurzschlüsse und auch Zeichen an einem Speicherort mit einer solchen Größe gespeichert werden. Um Java-Klassen nicht unbedingt aufzublähen, verzichtete man auf alle möglichen Kopiervarianten.
In ferner Zukunft könnte man erwarten, dass primitive Typen als generische Typparameter fungieren dürfen, sofern a List<int>. Dann könnten wir eine sehen Stream<char>.
Vermeiden Sie es im Moment besser charund verwenden Sie es möglicherweise java.text.Normalizerfür eine eindeutige kanonische Form von Codepunkten / Unicode-Zeichenfolgen.