Die einfache Antwort
Java 9 oder höher:
List<String> strings = List.of("foo", "bar", "baz");
Dadurch erhalten Sie eine unveränderlich List
Sie kann also nicht geändert werden.
Das ist das, was Sie in den meisten Fällen wollen, wenn Sie es vorbesetzen.
Java 8 oder früher:
List<String> strings = Arrays.asList("foo", "bar", "baz");
Dadurch erhalten Sie eine List
* durch ein Array unterstützt, so dass es seine Länge nicht ändern kann.
Aber Sie können anrufen List.set(...)
also ist es immer noch änderbar .
* Einzelheiten der Durchführung: Es ist eine private verschachtelte Klasse innerhalb von <code>java.util.Arrays</code> genannt. <code>ArrayList</code> ,<br>die eine andere Klasse ist als <code>java.util.ArrayList</code> obwohl ihre einfachen Namen die gleichen sind.
Statische Einfuhr
Sie können Java 8 Arrays.asList
noch kürzer mit einem statischen Import:
import static java.util.Arrays.asList;
...
List<String> strings = asList("foo", "bar", "baz");
Jede moderne IDE * wird dies für Sie vorschlagen und tun.
Ich empfehle nicht den statischen Import der List.of
Methode als nur of
weil es verwirrend ist.
* In IntelliJ IDEA drücken Sie zum Beispiel <code>Alt+Enter</code> und wählen Sie <code>Static import method...</code>
Verwendung von Stream
s
Warum muss es sich um eine List
?
Mit Java 8 oder höher können Sie eine Stream
die flexibler ist:
Stream<String> strings = Stream.of("foo", "bar", "baz");
Sie können verketten Stream
s:
Stream<String> strings = Stream.concat(Stream.of("foo", "bar"),
Stream.of("baz", "qux"));
Oder Sie können von einem Stream
zu einer List
:
import static java.util.stream.Collectors.toList;
...
var strings = Stream.of("foo", "bar", "baz").toList(); // Java 16
List<String> strings = Stream.of("foo", "bar", "baz").collect(toList()); // Java 8
Verwenden Sie aber vorzugsweise nur die Stream
ohne sie zu sammeln zu einem List
.
Wenn Sie speziell eine java.util.ArrayList
*
Wenn Sie möchten, dass beide eine Vorauswahl treffen ArrayList
et nachträglich hinzuzufügen, verwenden Sie
List<String> strings = new ArrayList<>(List.of("foo", "bar"));
strings.add("baz");
oder in Java 8 oder früher:
List<String> strings = new ArrayList<>(asList("foo", "bar"));
strings.add("baz");
oder mit Stream
:
import static java.util.stream.Collectors.toCollection;
List<String> strings = Stream.of("foo", "bar")
.collect(toCollection(ArrayList::new));
strings.add("baz");
Aber auch hier ist es besser, einfach die Stream
direkt, anstatt sie in einer List
.
* Sie brauchen wahrscheinlich nicht speziell eine <code>ArrayList</code> . Um zu zitieren <a href="http://openjdk.java.net/jeps/269" rel="noreferrer">GEP 269 </a>:
Es gibt eine <strong>kleiner Satz </strong>von Anwendungsfällen für die Initialisierung einer veränderlichen Sammlungsinstanz mit einem vordefinierten Satz von Werten. Normalerweise ist es besser, diese vordefinierten Werte in einer unveränderlichen Sammlung zu haben und dann die veränderliche Sammlung über einen Kopierkonstruktor zu initialisieren.
(Hervorhebung von mir)
Auf Schnittstellen programmieren, nicht auf Implementierungen
Sie sagten, Sie hätten die Liste als eine ArrayList
in Ihrem Code, aber das sollten Sie nur tun, wenn Sie ein Mitglied von ArrayList
die nicht in List
.
Was Sie höchstwahrscheinlich nicht tun.
Normalerweise sollten Sie Variablen nur über die allgemeinste Schnittstelle deklarieren, die Sie verwenden werden (z. B. Iterable
, Collection
o List
), und initialisieren sie mit der spezifischen Implementierung (z. B. ArrayList
, LinkedList
o Arrays.asList()
).
Andernfalls schränken Sie Ihren Code auf diesen speziellen Typ ein, und es wird schwieriger, ihn zu ändern, wenn Sie es wollen.
Wenn Sie zum Beispiel eine ArrayList
zu einer void method(...)
:
// Iterable if you just need iteration, for (String s : strings):
void method(Iterable<String> strings) {
for (String s : strings) { ... }
}
// Collection if you also need .size(), .isEmpty(), or .stream():
void method(Collection<String> strings) {
if (!strings.isEmpty()) { strings.stream()... }
}
// List if you also need random access, .get(index):
void method(List<String> strings) {
strings.get(...)
}
// Don't declare a specific list implementation
// unless you're sure you need it:
void method(ArrayList<String> strings) {
??? // You don't want to limit yourself to just ArrayList
}
Ein anderes Beispiel wäre, eine Variable immer als InputStream
auch wenn es sich in der Regel um eine FileInputStream
oder eine BufferedInputStream
denn eines Tages werden Sie oder jemand anderes eine andere Art von Werkzeug verwenden wollen. InputStream
.
43 Stimmen
Wenn dies für Unit-Tests gedacht ist, sollten Sie Groovy einmal ausprobieren. Sie können Ihren Testcode in Groovy schreiben, während Sie Java-Code testen, und mit
ArrasyList<String> places = ["Buenos Aires", "Córdoba", "La Plata"]
5 Stimmen
In Java SE 7 können Sie den parametrisierten Typ des Konstruktors durch eine leere Menge von Typparametern (<>) ersetzen: Map<String, List<String>> myMap = new HashMap<>();
2 Stimmen
Siehe auch stackoverflow.com/questions/157944/erstelle-arraylist-aus-array
2 Stimmen
Doppelte Klammern zur Initialisierung verwenden :)
0 Stimmen
Es scheint, dass Sie sich die Frage selbst beantwortet haben: ArrayList<String> places = new ArrayList<String>(asList("Buenos Aires", "Córdoba", "La Plata")); Arrays in Arrays.asList ist nicht erforderlich.
13 Stimmen
Stream.of("val1", "val2").collect(Collectors.toList()); //erzeugt ArrayList, Java8-Lösung.
0 Stimmen
Warum nicht einfach String [] places = {"Buenos Aires", "Córdoba", "La Plata"); ?
0 Stimmen
@PaulSmith Er könnte an einem elastischen Array interessiert sein, das dynamisch wachsen kann. Ihre Initialisierung macht Orte nur drei Elemente zu haben.
4 Stimmen
Ich verstehe nicht, warum wir nicht so etwas haben können wie
List<Integer> = {1, 2, 3, 4, 5}
in Java. Erstellen und init ein veränderbares Array in einer Zeile, wie ich weiß, Python und Swift könnte das tun.