Tại sao hai khái niệm khác nhau cả hai được gọi là heap tinh?


170

Tại sao heap runtime được sử dụng để cấp phát bộ nhớ động trong các ngôn ngữ kiểu C và cấu trúc dữ liệu được gọi là "heap"? Có một số mối quan hệ?


4
Tôi đã tự hỏi điều này ngày hôm nay trong khi nghiên cứu cấu trúc dữ liệu.
MitMaro


3
Đi đến một từ điển tiếng Anh và đếm số lượng mục trong "Chạy". Có bao nhiêu trong số hơn 40 mục áp dụng cho máy tính? :)
jmucchiello


Một bài viết liên quan ở đây wrt runtime heap được sử dụng để cấp phát bộ nhớ động.
RBT

Câu trả lời:


77

Donald Knuth nói (Nghệ thuật lập trình máy tính, Ed lần thứ ba, Tập 1, trang 435):

Một số tác giả bắt đầu khoảng năm 1975 để gọi nhóm bộ nhớ khả dụng là "đống".

Ông không nói tác giả nào và không đưa ra tài liệu tham khảo cho bất kỳ bài viết cụ thể nào, nhưng không nói rằng việc sử dụng thuật ngữ "heap" liên quan đến hàng đợi ưu tiên là ý nghĩa truyền thống của từ này.


11
Pool sẽ là một cái tên tốt hơn heap.

7
Hấp dẫn. Ai đó nên hỏi anh ta nếu anh ta nhớ những tác giả.
Giáo sư Falken

27
Wikipedia tuyên bố rằng đó là vì ở giai đoạn đầu Lisp đã sử dụng một đống (cấu trúc dữ liệu) để thực hiện lưu trữ bộ nhớ của nó. Nó không nói như thế nào. Tài liệu tham khảo của nó là "Thomas H. Cormen, Charles E. Leiserson, Ronald L. Rivest (1990): Giới thiệu về thuật toán. MIT Press / McGraw-Hill.", Mà tôi không có.
Steve Jessop

2
Tôi không có tài liệu tham khảo cho điều này nhưng tôi đoán rằng ban đầu cấu trúc dữ liệu được sử dụng để tổ chức các tham chiếu đến các khối bộ nhớ mở là một đống nhỏ. Có vẻ như đó sẽ là một cách tốt để nhanh chóng tìm ra khối bộ nhớ nhỏ nhất cho phép bạn lưu trữ dữ liệu mà bạn đang cố lưu trữ Cập nhật: Những gì tôi nói nghe giống hệt như khối bạn bè en.wikipedia.org/wiki/Docate_memory_allocation # Buddy% 5Fblocks
Sẽ

4
@SteveJessop - Kiểm tra Cormen, Leiserson, Rivest, Stein - phiên bản thứ 3 (2009) khi bắt đầu chương Heapsort, nó chỉ nói 'Thuật ngữ "heap" ban đầu được đặt ra trong bối cảnh của heapsort, nhưng nó đã được đề cập đến " lưu trữ được thu gom rác ", như ngôn ngữ lập trình Java và Lisp cung cấp. Cấu trúc dữ liệu heap của chúng tôi không phải là lưu trữ được thu gom rác và bất cứ khi nào chúng tôi đề cập đến các đống trong cuốn sách này, chúng tôi sẽ có nghĩa là một cấu trúc dữ liệu chứ không phải là một khía cạnh của bộ sưu tập rác. ' CLRS - Phiên bản thứ 2 cũng có phrasing gần như chính xác (không có dấu hiệu nào cho thấy Lisp đã sử dụng Heap).
dr jimbob

64

Chúng có cùng tên nhưng chúng thực sự không giống nhau (thậm chí về mặt khái niệm). Một đống bộ nhớ được gọi là một đống theo cùng một cách bạn sẽ gọi một giỏ giặt là "đống quần áo". Tên này được sử dụng để chỉ một nơi hơi lộn xộn, nơi bộ nhớ có thể được phân bổ và giải quyết theo ý muốn. Cấu trúc dữ liệu (như liên kết Wikipedia mà bạn tham chiếu chỉ ra) khá khác nhau.


8
Vâng, tôi nghĩ đó đúng hơn là điểm mà anh ấy dựa trên câu hỏi của mình: chúng khác nhau. Vậy tại sao chúng được gọi là cùng một thứ - có một số mối quan hệ cơ bản.
Sean Owen

9
Cách tôi diễn giải câu trả lời này là "không, không có mối quan hệ cơ bản", vì vậy nó trả lời câu hỏi.
Laurence Gonsalves

Andrew đang trả lời rằng. Không có quan hệ. Chỉ là tình cờ thôi. Heap bộ nhớ đúng hơn với cách sử dụng phổ biến vì bộ nhớ được phân bổ như thể một "đống quần áo". Cấu trúc dữ liệu tuy nhiên đòi hỏi một trí tưởng tượng lớn hơn. Và điều này trở thành một "lý do" khá thú vị hơn nhiều. Tên xuất phát từ các nút thực tế được sắp xếp bởi khóa của chúng và khóa nút cha luôn luôn> = so với nút con của nó.
Alexandre Bell

6
Họ chắc chắn không liên quan. Tuy nhiên, vấn đề với việc gọi nó là "heap" là "đối tác của heap -" stack "- cũng là một stack thực sự.
dan

1
Tôi biết tại sao cấu trúc dữ liệu heap được gọi là heap: bởi vì nó thỏa mãn thuộc tính heap. Nhưng tại sao tài sản heap được gọi như vậy? Nó không có ý nghĩa với tôi, vì một cái tên như "nặng hàng đầu" sẽ tốt hơn nhiều.
Thomas Eding

31

Sự va chạm tên là không may, nhưng không phải là tất cả bí ẩn. Heap là một từ nhỏ, phổ biến được sử dụng để chỉ một đống, bộ sưu tập, nhóm, v.v ... Việc sử dụng từ này cho cấu trúc dữ liệu trước ngày (tôi khá chắc chắn) tên của nhóm bộ nhớ. Trong thực tế, pool sẽ là một lựa chọn tốt hơn nhiều cho cái sau, theo ý kiến ​​của tôi. Heap bao hàm một cấu trúc dọc (giống như một đống), phù hợp với cấu trúc dữ liệu, nhưng không phải là nhóm bộ nhớ. Chúng ta không nghĩ rằng một đống bộ nhớ là phân cấp, trong khi ý tưởng cơ bản đằng sau cấu trúc dữ liệu là giữ phần tử lớn nhất ở đầu heap (và heap phụ).

Heap cấu trúc dữ liệu có từ giữa những năm 60; đống bộ nhớ, đầu những năm 70 Thuật ngữ heap (có nghĩa là nhóm bộ nhớ) đã được sử dụng ít nhất là vào năm 1971 bởi Wijngaarden trong các cuộc thảo luận về Algol.

Có thể việc sử dụng heap sớm nhất như một cấu trúc dữ liệu được tìm thấy bảy năm trước đó trong
Williams, JWJ 1964. "Thuật toán 232 - Heapsort", Truyền thông của ACM 7 (6): 347-348


1
Có, nhưng một đống cũng ngụ ý rối loạn và đống bộ nhớ thường bị rối loạn. Heap cấu trúc dữ liệu được sắp xếp rất tốt. Vì vậy, một lần nữa có một sự không phù hợp bằng nhau đi theo cách khác dựa trên định nghĩa chung của heap.
jmucchiello

Nó luôn được giới thiệu là đối diện của stack , đủ để giải thích tên IMO.
Revierpost

1
Không phải ngẫu nhiên - danh sách miễn phí có thể được triển khai như một hàng đợi ưu tiên thông qua một đống nhị thức.
Heath Hunnicutt

2
@jmucchiello: một đống các bản ghi (xem hình ) được sắp xếp tốt và giống như cây. Đây là nguồn gốc của tên cấu trúc dữ liệu theo một trong những cuốn sách giáo khoa đại học của tôi.
gioele

6

Trên thực tế, đọc về cách phân bổ bộ nhớ (xem Khối Buddy ) nhắc nhở tôi về một đống trong cấu trúc dữ liệu.


Nhận xét của tôi về câu trả lời của Peter Zhang cũng có liên quan ở đây. Hệ thống bạn bè nhị phân có thể được biểu diễn dưới dạng cây nhị phân và nó cũng trông giống như một heap tối đa hợp lệ thực hiện khi "khóa" của mỗi nút là tổng bộ nhớ bên dưới nó (nhưng các giá trị này là ẩn và không bao giờ thay đổi). Cả thuật toán cấp phát và giải phóng đều không sử dụng các hoạt động heap trên cây nhị phân này, theo như tôi có thể nói.
Eric Dubé

5

IMO nó chỉ đơn thuần là một tai nạn / sự trùng hợp ngẫu nhiên mà hai thứ hoàn toàn không liên quan này có cùng tên. Nó giống như đồ thịđồ thị .


Hai biểu đồ có thể mặc dù bằng cách nào đó có liên quan. Tưởng tượng đồ thị của một hàm như sau: Miền tuple, phạm vi) là một đỉnh và một cạnh kết nối hai đỉnh như vậy

2
@Amit: Đối với các biểu đồ liên tục có nghĩa là vô số đỉnh. Điều này là ổn, nhưng điều đó cũng làm cho khái niệm các cạnh giữa các đỉnh trở nên vô nghĩa. Trong đồ thị của hàm f (x) = x * 2, có cạnh giữa (0,0) và (1,2) không? Nếu có, làm thế nào về (0,0) và (0,5,1)? (0,0) và (0,25,0,5)? Không có cách nào có khái niệm cạnh giữa các đỉnh, vì vậy đây không thực sự là một biểu đồ.
MAK

5

Cấu trúc dữ liệu giống như đống được sử dụng bởi thuật toán tìm phân bổ bộ nhớ có sẵn. Sau đây được trích từ http://www.cprogramming.com/tutorial/virtual_memory_and_heaps.html .

Khi newđược gọi, nó bắt đầu tìm kiếm một khối bộ nhớ miễn phí phù hợp với kích thước cho yêu cầu của bạn. Giả sử rằng một khối bộ nhớ như vậy được tìm thấy, nó được đánh dấu là dành riêng và một con trỏ đến vị trí đó được trả về. Có một số thuật toán để thực hiện điều này bởi vì phải thỏa hiệp giữa việc quét toàn bộ bộ nhớ để tìm khối tự do nhỏ nhất lớn hơn kích thước của đối tượng của bạn hoặc trả lại khối đầu tiên nơi bộ nhớ cần phù hợp. Để cải thiện tốc độ lấy một khối bộ nhớ, các vùng bộ nhớ trống và dành riêng được duy trì trong cấu trúc dữ liệu tương tự như cây nhị phân gọi là heap.


1
Tôi cực kỳ nghi ngờ về điều này, cụ thể là "... các vùng bộ nhớ trống và dành riêng được duy trì trong một cấu trúc dữ liệu tương tự như cây nhị phân gọi là một đống." Nghe có vẻ như tác giả đang đoán có một kết nối, dựa trên tên "heap", và có lẽ bị nhầm lẫn. Bất cứ ai có thể xác nhận / bác bỏ?
Don nở

1
Sau một số nghiên cứu nhẹ về hệ thống Binary Buddy (được sử dụng trong Linux), nó có thể được biểu diễn bằng cây nhị phân do cách phân vùng dữ liệu. Cây nhị phân này trông giống như một đống tối đa hợp lệ nếu bạn quan sát các nút theo tổng bộ nhớ, nhưng các nút không được chèn vào cây nhị phân này khi chúng nằm trong một đống tối đa - các nút được chèn trực tiếp vào lá nhỏ nhất của bộ nhớ trống> = kích thước yêu cầu. 1 2 3
Eric Dubé

1

Các thuật ngữ thông tục ngăn xếp bộ nhớ ngăn xếp và bộ nhớ heap không được sử dụng trong tiêu chuẩn C ++. Tiêu chuẩn sử dụng lưu trữ tĩnh, lưu trữ luồng, lưu trữ tự động và lưu trữ động.

Nhiều hơn có thể được tìm thấy tại phần Storage Duraction của tiêu chuẩn.

Do đó, từ quan điểm của ngôn ngữ và thư viện tiêu chuẩn, không có sự nhầm lẫn.


1

Q. một đống là gì? A. Một đống là một tập hợp các đối tượng đặt chồng lên nhau.

Trả lời cho câu hỏi của bạn: Cả heap bộ nhớ và heap nhị phân đều sử dụng cùng một khái niệm như bạn biết. Dữ liệu được lưu trữ dưới dạng một đống trong bộ nhớ theo thứ tự như được ghi trong chương trình trong khi heap nhị phân là một cấu trúc dữ liệu theo cùng một khái niệm lưu trữ dữ liệu theo cách có thứ tự dưới dạng heap (Dữ liệu trên cùng của những thứ còn lại). Hãy cho tôi biết những gì bạn nghĩ trong phần bình luận.


-2

Có lẽ heap bộ nhớ đầu tiên được thực hiện được quản lý bởi một cấu trúc heap?


8
Giả thuyết đó dường như hoàn toàn không rõ ràng - làm thế nào một heap (cấu trúc dữ liệu) hoàn toàn hữu ích để duy trì một heap (vùng nhớ động)?
Keith Randall

7
-1. Tôi muốn một tuyên bố có thẩm quyền với bằng chứng thay vì những gì rõ ràng chỉ là một phỏng đoán.
Rob Kennedy

Bất thường. Dường như không có lý do chính đáng để sử dụng một heap (cấu trúc dữ liệu) để quản lý heap (nhóm bộ nhớ trống).
jason
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.