Ngoài thuật toán "peek at the top of the heap" được đề xuất, thuật toán này cung cấp cho bạn độ phức tạp O (n log m) để nhận được nhiều mục hàng đầu, sau đây là hai giải pháp khác.
Giải pháp 1: Sử dụng vùng đệm Fibonacci.
Việc triển khai PriorityQueue của JDK là một đống nhị phân cân bằng. Bạn sẽ có thể ép thêm hiệu suất từ việc thực hiện Fibonacci heap. Nó sẽ có thời gian chèn không đổi được khấu hao, trong khi chèn vào một đống nhị phân có độ phức tạp Ω (log n) theo kích thước của vùng heap. Nếu bạn làm điều đó cho mọi phần tử, thì bạn đang ở Ω (n log n). Việc tìm kiếm trên cùng của n mục bằng cách sử dụng một đống heap có độ phức tạp O (n + m log n). Kết hợp điều này với gợi ý để chỉ bao giờ chèn các phần tử m vào heap, và bạn có O (n + m log m), gần với thời gian tuyến tính như bạn sẽ nhận được.
Giải pháp 2: Traverse danh sách M lần.
Bạn sẽ có thể lấy phần tử lớn thứ k trong một bộ trong thời gian O (n). Chỉ cần đọc mọi thứ vào danh sách và thực hiện như sau:
kthLargest(k, xs)
Pick a random pivot element p from the list
(the first one will do if your list is already random).
Go over the set once and group it into two lists.
Left: smaller than p.
Right: Larger or equal to p.
If the Right list is shorter than k, return kthLargest(k - right.size, Left)
If the Right list is longer than k, return kthLargest(k, right)
Otherwise, return p.
Điều đó cho bạn thời gian O (n). Chạy thời gian đó m, bạn sẽ có thể nhận được các đối tượng top-m trong bộ của bạn trong thời gian O (nm), mà sẽ được nghiêm ngặt ít hơn n log n cho đủ lớn n và đủ nhỏ m. Ví dụ, nhận được top-10 trên một triệu mục sẽ mất một nửa miễn là sử dụng hàng đợi ưu tiên heap nhị phân, tất cả những thứ khác bằng nhau.
Bạn có chạy profiler trên mã này không? So sánh của bạn được viết như thế nào? –
public int compare (ListElement i, ListElement j) { \t \t \t \t \t \t \t if (i.getValue() - j.getValue()> 0) trở lại 1; else trả lại -1; } – BigG
Id đánh giá cao đề xuất bạn nên cấu hình mã của bạn và tìm hiểu chính xác những gì đang khiến mã của bạn chạy chậm hơn bạn muốn. Không có mã được hiển thị và không có thông tin bổ sung, thật khó để trả lời câu hỏi này. Phần nào đang chạy chậm? –