Các thư viện Boost C ++ bao gồm việc triển khai các đống Fibonacci trong boost/pending/fibonacci_heap.hpp
. Tập tin này rõ ràng đã tồn tại trong pending/
nhiều năm và bởi những dự đoán của tôi sẽ không bao giờ được chấp nhận. Ngoài ra, đã có lỗi trong quá trình thực hiện, được sửa chữa bởi người quen của tôi và anh chàng lạnh lùng xung quanh Aaron Windsor. Thật không may, hầu hết các phiên bản của tệp mà tôi có thể tìm thấy trực tuyến (và phiên bản trong gói libboost-dev của Ubuntu) vẫn có lỗi; Tôi đã phải lấy một phiên bản sạch từ kho Subversion.
Kể từ phiên bản 1.49, các thư viện Boost C ++ đã thêm rất nhiều cấu trúc heaps mới bao gồm cả đống heap.
Tôi đã có thể biên dịch dijkstra_heap_performance.cpp dựa trên phiên bản sửa đổi của dijkstra_shortest_paths.hpp để so sánh các heap Fibros và heap nhị phân. (Trong dòng typedef relaxed_heap<Vertex, IndirectCmp, IndexMap> MutableQueue
, thay đổi relaxed
thành fibonacci
.) Trước tiên tôi quên biên dịch với các tối ưu hóa, trong trường hợp đó, các heap nhị phân và nhị phân thực hiện như nhau, với các heap Fibros thường vượt trội hơn một lượng không đáng kể. Sau khi tôi biên dịch với tối ưu hóa rất mạnh, các đống nhị phân đã có một sự thúc đẩy to lớn. Trong các thử nghiệm của tôi, các heap Fibros chỉ vượt trội so với heap nhị phân khi đồ thị cực kỳ lớn và dày đặc, ví dụ:
Generating graph...10000 vertices, 20000000 edges.
Running Dijkstra's with binary heap...1.46 seconds.
Running Dijkstra's with Fibonacci heap...1.31 seconds.
Speedup = 1.1145.
Theo như tôi hiểu, điều này chạm đến sự khác biệt cơ bản giữa các đống Fibonacci và đống nhị phân. Sự khác biệt lý thuyết thực sự duy nhất giữa hai cấu trúc dữ liệu là các heap Fibros hỗ trợ khóa giảm trong thời gian không đổi (khấu hao). Mặt khác, các đống nhị phân có được rất nhiều hiệu suất từ việc thực hiện như một mảng; sử dụng một cấu trúc con trỏ rõ ràng có nghĩa là các đống Fibonacci phải chịu một hiệu suất rất lớn.
Do đó, để hưởng lợi từ các đống Fibonacci trong thực tế , bạn phải sử dụng chúng trong một ứng dụng trong đó giảm_key là cực kỳ thường xuyên. Về mặt Dijkstra, điều này có nghĩa là đồ thị cơ bản dày đặc. Một số ứng dụng về bản chất có thể giảm_key-cường độ cao; Tôi muốn thử thuật toán cắt tối thiểu Nagomochi-Ibaraki vì rõ ràng nó tạo ra rất nhiều hàm giảm, nhưng quá nhiều nỗ lực để làm cho một phép so sánh thời gian hoạt động.
Cảnh báo : Tôi có thể đã làm điều gì đó sai. Bạn có thể muốn thử tái tạo những kết quả này cho mình.
Lưu ý về mặt lý thuyết : Hiệu suất được cải thiện của các đống Fibonacci trên less_key rất quan trọng đối với các ứng dụng lý thuyết, chẳng hạn như thời gian chạy của Dijkstra. Các đống Fibonacci cũng vượt trội so với các đống nhị phân khi chèn và sáp nhập (cả hai đều được khấu hao theo thời gian không đổi cho các đống Fibonacci). Việc chèn về cơ bản là không liên quan, vì nó không ảnh hưởng đến thời gian chạy của Dijkstra và việc sửa đổi các đống nhị phân cũng khá dễ dàng để chèn vào thời gian không đổi. Hợp nhất trong thời gian liên tục là tuyệt vời, nhưng không liên quan đến ứng dụng này.
Lưu ý cá nhân : Một người bạn của tôi và tôi đã từng viết một bài báo giải thích về hàng đợi ưu tiên mới, cố gắng sao chép thời gian chạy (lý thuyết) của đống Fibonacci mà không phức tạp. Bài báo chưa bao giờ được xuất bản, nhưng đồng tác giả của tôi đã thực hiện các đống nhị phân, các đống Fibonacci và hàng đợi ưu tiên của chúng ta để so sánh các cấu trúc dữ liệu. Các biểu đồ của các kết quả thử nghiệm chỉ ra rằng các heap nhị phân được thực hiện một chút so với các heap nhị phân được thực hiện một cách tổng thể so với tổng số so sánh, cho thấy các heap của Fibonacci sẽ hoạt động tốt hơn trong trường hợp chi phí so sánh vượt quá chi phí. Thật không may, tôi không có sẵn mã và có lẽ trong so sánh tình huống của bạn là rẻ, vì vậy những nhận xét này có liên quan nhưng không thể áp dụng trực tiếp.
Ngẫu nhiên, tôi đặc biệt khuyên bạn nên cố gắng khớp thời gian chạy của các đống Fibonacci với cấu trúc dữ liệu của riêng bạn. Tôi thấy rằng tôi chỉ đơn giản là phát minh lại đống Fibonacci. Trước đây tôi nghĩ rằng tất cả sự phức tạp của các đống Fibonacci là một số ý tưởng ngẫu nhiên, nhưng sau đó tôi nhận ra rằng tất cả chúng đều tự nhiên và khá gượng ép.