To convert Set to List in Java, we pass the set to the ArrayList constructor, as in new ArrayList<>(set), which copies every element into a new, modifiable list. For a read-only list, we use List.copyOf(set) or set.stream().toList(), and for the opposite direction, new HashSet<>(list) turns a list into a set and drops its duplicates.
We convert a set to a list when we need what only a list offers, such as access by index, sorting, or an order we control. A typical case is a set of unique tags that a page must show sorted and split into pages of ten.
The following example converts a set of fruits to a list in three ways and turns a list back into a set.
Set<String> fruits = new LinkedHashSet<>(List.of("banana", "apple", "cherry"));
List<String> list = new ArrayList<>(fruits); // [banana, apple, cherry]
List<String> readOnly = List.copyOf(fruits); // [banana, apple, cherry]
List<String> sorted = fruits.stream().sorted().toList(); // [apple, banana, cherry]
Set<String> unique = new LinkedHashSet<>(List.of("kiwi", "fig", "kiwi")); // [kiwi, fig]
The converted list keeps the iteration order of the set, which is insertion order for a LinkedHashSet. We cover the order we get from each set type, sorted and unmodifiable results, and the list-to-set direction with its own traps.
1. Convert Set to List with the ArrayList Constructor
The constructor ArrayList(Collection) accepts any collection, so it converts a HashSet, a LinkedHashSet or a TreeSet in one step. It copies the elements in the order the set’s iterator returns them, and the new ArrayList is independent of the set.
Set<Integer> ids = new TreeSet<>(Set.of(30, 10, 20));
List<Integer> idList = new ArrayList<>(ids); // [10, 20, 30]
idList.add(40); // idList = [10, 20, 30, 40]
int first = idList.get(0); // 10
When the target list already exists, addAll() appends the set elements to it instead of creating a new list.
Set<String> extras = new LinkedHashSet<>(List.of("nuts", "honey"));
List<String> toppings = new ArrayList<>(List.of("cream"));
toppings.addAll(extras); // toppings = [cream, nuts, honey]
2. Order of Elements after the Conversion
The list gets the same order in which the set iterates, so the set type decides the order of the list. A HashSet promises no order at all, a LinkedHashSet keeps insertion order, and a TreeSet keeps its elements sorted.

List<String> input = List.of("banana", "apple", "cherry");
List<String> fromLinked = new ArrayList<>(new LinkedHashSet<>(input)); // [banana, apple, cherry]
List<String> fromTree = new ArrayList<>(new TreeSet<>(input)); // [apple, banana, cherry]
List<String> fromHash = new ArrayList<>(new HashSet<>(input)); // all three, order not defined
Code that reads list.get(0) after converting a HashSet works by chance. The order can change when we add elements or move to another JDK version, so tests that compare the list with a fixed order become flaky.
Since Java 21, LinkedHashSet and TreeSet implement SequencedSet from the sequenced collections API. We can read the first and last element without a conversion, or build a list in reverse order with reversed().
SequencedSet<String> recent = new LinkedHashSet<>(List.of("home", "cart", "checkout"));
String firstPage = recent.getFirst(); // "home"
List<String> newestFirst = new ArrayList<>(recent.reversed()); // [checkout, cart, home]
3. Convert a Set to an Unmodifiable List
When the list must not change, we create an unmodifiable copy. Java offers two methods, and they differ only in how they treat null elements.
- The method List.copyOf() (Java 10) throws NullPointerException if the set contains null.
- The method Stream.toList() (Java 16) accepts null elements.
Set<String> sizes = new LinkedHashSet<>(Arrays.asList("S", null, "M"));
List<String> viaStream = sizes.stream().toList(); // [S, null, M]
List<String> viaCopyOf = List.copyOf(sizes); // NullPointerException
Both lists throw UnsupportedOperationException on add(), remove() or set(). A class that returns its internal set to callers as a list uses one of them, so callers cannot change the data, as described in collecting a stream into an immutable collection.
4. Convert a Set to a Sorted List
An online store keeps the tags of all products in a HashSet, because a tag must appear once no matter how many products use it. The tag filter on the website needs those tags in alphabetical order, so the backend converts the set to a sorted list before it sends the JSON response.
Set<String> tags = new HashSet<>(Set.of("sale", "new", "eco", "kids"));
List<String> filterTags = tags.stream().sorted().toList(); // [eco, kids, new, sale]
List<String> byLength = new ArrayList<>(tags);
byLength.sort(Comparator.comparingInt(String::length).thenComparing(Comparator.naturalOrder()));
String result = byLength.toString(); // "[eco, new, kids, sale]"
A sorted stream fits when the list is read-only. For a modifiable list, we copy the set into an ArrayList and call sort(), which also accepts any Comparator, as shown in sorting an ArrayList.
5. Convert a List to a Set
The opposite conversion uses the constructor of the set class. Since a set holds each element once, the conversion removes duplicates, and the set type decides the order again.
List<Integer> votes = List.of(3, 1, 3, 2, 1);
Set<Integer> hashed = new HashSet<>(votes); // 1, 2 and 3, order not defined
Set<Integer> inOrder = new LinkedHashSet<>(votes); // [3, 1, 2]
Set<Integer> ascending = new TreeSet<>(votes); // [1, 2, 3]
Set<Integer> frozen = Set.copyOf(votes); // 1, 2 and 3, unmodifiable
int count = hashed.size(); // 3
The method Set.copyOf() drops duplicates without an exception, but the factory method Set.of() throws IllegalArgumentException when we pass the same element twice. For streams, Collectors.toSet() does not guarantee the set type, so we use Collectors.toCollection(LinkedHashSet::new) when the order matters.
Set<String> fromCopy = Set.copyOf(List.of("a", "a")); // [a]
Set<String> fromOf = Set.of("a", "a"); // IllegalArgumentException: duplicate element: a
Set<String> fromStream = Stream.of("b", "a", "b").collect(Collectors.toCollection(LinkedHashSet::new)); // [b, a]
Converting a list to a set and back is the classic way to remove duplicates from a list. With a LinkedHashSet in the middle, the result keeps the first occurrence of each element in the original order.
6. Using Guava
Projects that use Guava can call Lists.newArrayList(set) for a modifiable list and ImmutableList.copyOf(set) for an immutable one. Both give the same result as the JDK methods in section 1 and section 3, so Guava is not needed for this conversion alone.
Set<String> fruits = new TreeSet<>(Set.of("plum", "lime"));
List<String> guavaList = Lists.newArrayList(fruits); // [lime, plum]
List<String> guavaImmutable = ImmutableList.copyOf(fruits); // [lime, plum]
7. Set and List Conversion FAQs
Search results for Set to List conversion show the same follow-up questions about order, indexes and arrays.
7.1. Does converting a HashSet to an ArrayList keep the order?
The list keeps the iteration order of the HashSet, but that order is not defined, so it can differ from the insertion order and from the sorted order. We use a LinkedHashSet for insertion order or a TreeSet for sorted order.
7.2. Can we get an element by index from a Set?
No. The Set interface has no get(int) method, because most sets have no positions. We convert to a list for index access, or we use getFirst() and getLast() on a LinkedHashSet or TreeSet since Java 21.
7.3. How do we convert a Set to an array?
We call toArray() with an array constructor reference, which returns an array of the right type.
Set<String> colors = new TreeSet<>(Set.of("red", "blue"));
String[] array = colors.toArray(String[]::new); // [blue, red]
7.4. Is new ArrayList<>(set) or set.stream().toList() faster?
Both copy every element once, so both take time proportional to the size of the set. The real difference is the result, because the constructor returns a modifiable ArrayList and toList() returns an unmodifiable list.
8. Conclusion
We convert a Set to a List with new ArrayList<>(set) when the list must change, and with List.copyOf() or stream().toList() when it must not. The list always gets the iteration order of the set, so we pick a LinkedHashSet or a TreeSet when the order matters, or sort the result.
In the other direction, a set constructor turns a list into a set and drops the duplicates. The method Set.copyOf() accepts duplicates, whereas Set.of() rejects them with IllegalArgumentException.
9. References
- ArrayList(Collection) Javadoc
- List.copyOf() Javadoc
- Set.copyOf() Javadoc
- HashSet Javadoc
- SequencedSet Javadoc
Happy Learning !!