Java Đặt thứ tự giữ lại?


179

Bộ Java có giữ trật tự không? Một phương thức đang trả về một Set cho tôi và được cho là dữ liệu được sắp xếp nhưng lặp lại trên Set, dữ liệu không được sắp xếp. Có cách nào tốt hơn để quản lý này? Có phải thay đổi phương thức để trả về một cái gì đó không phải là Set không?


3
"Các phần tử được trả về không theo thứ tự cụ thể (trừ khi tập hợp này là một thể hiện của một số lớp cung cấp bảo đảm)." là những gì phương thức lặp cho một tập hợp nói. tìm thấy ở đây
keyer

Câu trả lời:


256

Các Setgiao diện không cung cấp bất kỳ bảo đảm trật tự.

Giao diện phụ của nó SortedSetđại diện cho một bộ được sắp xếp theo một số tiêu chí. Trong Java 6, có hai thùng chứa tiêu chuẩn thực hiện SortedSet. Họ là TreeSetConcurrentSkipListSet.

Ngoài SortedSetgiao diện, còn có LinkedHashSetlớp. Nó nhớ thứ tự các phần tử được chèn vào tập hợp và trả về các phần tử của nó theo thứ tự đó.


21
Hơn nữa, do băm Chuỗi khác nhau trong Java 8, thứ tự mặc định (chưa được sắp xếp) trong Bộ và Bản đồ sẽ thay đổi. Nếu bạn dựa vào thứ tự chưa được sắp xếp, mã của bạn sẽ hoạt động khác theo Java 8.
rustyx

Tôi nhận thấy rằng lớp không đặt hàng là bình thường, nhưng hành vi mà tôi mong đợi là rời khỏi chúng khi chúng được giới thiệu và không gây rối với trật tự, thay vào đó chỉ là xáo trộn các yếu tố mỗi khi tổng hợp. Giải pháp của bạn không khô héo tối ưu vì sau đó tôi sẽ phải triển khai toàn bộ cấu trúc để chúng được sắp xếp CÙNG CÁCH mà chúng được giới thiệu: S
White_King

@White_King: Một tập hợp là một khái niệm toán học không chứa khái niệm "thứ tự chèn", vì vậy nó có ý nghĩa cho giao diện Java tuân theo các quy ước của nó. Có các tập hợp được sắp xếp nhưng thứ tự được chỉ định bởi một mối quan hệ (bộ so sánh trong Java), một lần nữa khớp với định nghĩa trong lý thuyết tập hợp với định nghĩa trong Java. Kỳ vọng của bạn về việc giữ thứ tự chèn có thể đến từ danh sách nhưng bộ không phải là danh sách.
Konrad Höffner

103

LinkedHashSet là những gì bạn cần.


43
A Listkhông phải là một Set(nó không đảm bảo tính duy nhất của thành viên).
Chuộc tội có giới hạn

10
Trong nhiều trường hợp kinh doanh duy nhất, Danh sách không thể được sử dụng chỉ để giữ lại đơn hàng thay vì Đặt. LinkedHashSet duy trì trật tự và lưu trữ duy nhất.
gub

18

Vì nhiều thành viên đề nghị sử dụng LinkedHashset để giữ thứ tự của bộ sưu tập. Bạn có thể gói thiết lập của bạn bằng cách sử dụng thực hiện này.

Việc triển khai Sắp xếp có thể được sử dụng cho thứ tự đã sắp xếp nhưng cho mục đích của bạn, hãy sử dụng LinkedHashset .

Cũng từ các tài liệu,

"Việc triển khai này tránh khách hàng của mình khỏi đơn đặt hàng không xác định, nói chung là hỗn loạn do Hashset cung cấp, mà không phải chịu chi phí gia tăng liên quan đến Treeset. Nó có thể được sử dụng để tạo một bản sao của một bộ có cùng thứ tự như ban đầu, bất kể bản gốc thiết lập triển khai: "

Nguồn: http://docs.oracle.com/javase/6/docs/api/java/util/LinkedHashSet.html


9

Set chỉ là một giao diện. Để giữ lại trật tự, bạn phải sử dụng một triển khai cụ thể của giao diện đó và Giao diện phụ Sắp xếp, ví dụ như PlantsSet hoặc LinkedHashset. Bạn có thể gói Set theo cách này:

Set myOrderedSet = new LinkedHashSet(mySet);

7

Dưới đây là một bản tóm tắt nhanh về các đặc điểm thứ tự của các Settriển khai tiêu chuẩn có sẵn trong Java:

  1. giữ thứ tự chèn: LinkedHashsetCopyOnWriteArraySet (thread-safe)
  2. giữ các mục được sắp xếp trong tập hợp: TreeSet , Enumset (cụ thể cho enums) và ConcurrencySkipListSet (thread-safe)
  3. không giữ các mục theo bất kỳ thứ tự cụ thể nào: Hashset (cái bạn đã thử)

Đối với trường hợp cụ thể của bạn, bạn có thể sắp xếp các mục trước và sau đó sử dụng bất kỳ 1 hoặc 2 (rất có thể LinkedHashSethoặc TreeSet). Hoặc cách khác và hiệu quả hơn , bạn chỉ có thể thêm dữ liệu chưa được sắp xếp vào một dữ liệu TreeSetsẽ tự động sắp xếp cho bạn.


7

Để giữ lại thứ tự sử dụng Listhoặc a LinkedHashSet.


1
Đó là LinkedHashSet, không ... Map.
Marko Topolnik

Tôi cần một Set không phải là List, tôi cần Set mà CSONG giữ nguyên thứ tự tiêm của các đối tượng tôi đoán
White_King

5

LinkedHashset là phiên bản được đặt hàng của Hashset duy trì Danh sách liên kết đôi trên tất cả các yếu tố. Sử dụng lớp này thay vì Hashset khi bạn quan tâm đến thứ tự lặp.


3

Từ javadoc cho Set.iterator():

Trả về một trình vòng lặp qua các phần tử trong bộ này. Các phần tử được trả về không theo thứ tự cụ thể (trừ khi tập hợp này là một thể hiện của một số lớp cung cấp bảo đảm).

Và, như đã được shuuchan tuyên bố , a TreeSetlà một triển khai Setcó một trật tự được bảo đảm:

Các phần tử được sắp xếp theo thứ tự tự nhiên của chúng hoặc bởi Bộ so sánh được cung cấp tại thời điểm tạo đã đặt, tùy thuộc vào hàm tạo nào được sử dụng.


3

Thông thường, thiết lập không giữ thứ tự, chẳng hạn như Hashset để nhanh chóng tìm thấy một phần mềm, nhưng bạn có thể thử LinkedHashset, nó sẽ giữ thứ tự mà bạn đặt.


1

Có 2 điều khác nhau.

  1. Sắp xếp các yếu tố trong một bộ. Mà chúng tôi đã Sắp xếp và triển khai tương tự.
  2. Duy trì thứ tự chèn trong một bộ. Đối với LinkedHashset và CopyOnWriteArraySet (thread-safe) có thể được sử dụng.



-2

Chỉ SortedSetcó thể làm theo thứ tự củaSet


Câu hỏi là về việc giữ lại thứ tự chèn (điều này sẽ được sắp xếp).
assylias
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.