Cây tìm kiếm nhị phân cân bằng là rất cần thiết để đảm bảo tra cứu O (log n) (hoặc các hoạt động tương tự). Trong một môi trường năng động, nơi có rất nhiều khóa được chèn và / hoặc xóa ngẫu nhiên, cây có thể bị thoái hóa thành các danh sách được liên kết, điều này thật kinh khủng cho việc tra cứu. Do đó, có nhiều loại cây nhị phân tự cân bằng khác nhau chống lại hiệu ứng này (chẳng hạn như cây AVL hoặc cây splay ). Những cây này dựa trên các loại luân chuyển khác nhau để cân bằng lại cây.
Xoay
Trong thử thách này, chúng ta sẽ chỉ nhìn vào các góc quay phải, một vòng quay như vậy (xoay trái sẽ đối xứng) trông như thế này:
5 3
/ \ / \
3 6 => 1 5
/ \ / \
1 4 4 6
Nếu bất kỳ lá nào 1
, 4
hoặc 6
có cây con trái hoặc phải, một vòng quay sẽ chỉ đơn giản là giữ chúng ở đó. Nếu đây là cây con của cây lớn hơn, chúng ta chỉ cần "cắt nó" tại nút 5
và "gắn lại" cây đã xoay (nút bây giờ 3
) vào nút đó.
Thử thách
Cho cây tìm kiếm nhị phân 1 và khóa phải xoay cây trên nút đó như mô tả ở trên. Khóa được cung cấp trong ví dụ trên sẽ là 5
.
Quy tắc và I / O
- bạn có thể sử dụng bất kỳ loại nào cho các khóa miễn là có một sự lựa chọn giữa các khóa bạn chọn và các trường hợp kiểm tra
- bạn có thể chọn bất kỳ đại diện nào cho cây nhị phân miễn là không có sự mơ hồ (ví dụ:
[3,[]]
không rõ ràng trừ khi có quy định khác) và đó là điều tự nhiên đối với ngôn ngữ bạn chọn - vì đầu vào sẽ luôn là cây tìm kiếm nhị phân, không có khóa trùng lặp
- bạn có thể cho rằng chìa khóa được chứa trong cây
- bạn có thể cho rằng nút chứa khóa có con trái
- bạn không thể sử dụng một cây con đúng theo khóa được cung cấp
- bạn không thể cho rằng cây bị mất cân bằng trước khi xoay
- bạn không thể cho rằng cây được cân bằng sau khi xoay
- bạn có thể sử dụng bất kỳ phương pháp I / O mặc định nào
- trình của bạn có thể là một hàm trả về cây hoặc chương trình đầy đủ in giải pháp
Các trường hợp thử nghiệm
Những ví dụ này đại diện cho một cây như sau
- nếu đó là một chiếc lá:
[]
- nếu đó là một cây có chìa khóa
x
và cả hai cây con đều là lá:[x]
- nếu đó là một cây có chìa khóa
x
và cây conleft
right
:[x,left,right]
Ví dụ đầu tiên là ví dụ được cung cấp trong phần Xoay vòng . Nếu vì lý do nào đó bạn cần một đại diện đồ họa của họ, ở đây 2 bạn đi.
5 [5,[3,[1],[4]],[6]] -> [3,[1],[5,[4],[6]]]
5 [5,[3,[1],[4]],[]] -> [3,[1],[5,[4],[]]]
5 [5,[3,[],[4]],[6]] -> [3,[],[5,[4],[6]]]
5 [5,[3,[1],[]],[]] -> [3,[1],[5]]
4 [8,[4,[2,[1],[3]],[6,[5],[7]]],[12,[10,[9],[11]],[14,[13],[15]]]] -> [8,[2,[1],[4,[3],[6,[5],[7]]]],[12,[10,[9],[11]],[14,[13],[15]]]]
8 [10,[8,[6,[4,[2,[],[3]],[5]],[7]],[9]],[11]] -> [10,[6,[4,[2,[],[3]],[5]],[8,[7],[9]]],[11]]
10 [10,[8,[6,[4,[2,[],[3]],[5]],[7]],[9]],[11]] -> [8,[6,[4,[2,[],[3]],[5]],[7]],[10,[9],[11]]]
9 [6,[3,[2],[5]],[9,[8],[12,[11],[15,[14],[]]]]] -> [6,[3,[2],[5]],[8,[],[9,[],[12,[11],[15,[14],[]]]]]]
7 [7,[5,[3,[1],[4]],[6]],[8]] -> [5,[3,[1],[4]],[7,[6],[8]]]
15 [17,[9,[5,[2,[0],[4]],[8]],[15,[13,[11,[10],[12]],[14]],[16]]],[40,[27,[21,[19,[18],[20]],[24,[22],[25]]],[28]],[44,[42,[41],[]],[51,[47],[59,[55],[61]]]]]] -> [17,[9,[5,[2,[0],[4]],[8]],[13,[11,[10],[12]],[15,[14],[16]]]],[40,[27,[21,[19,[18],[20]],[24,[22],[25]]],[28]],[44,[42,[41],[]],[51,[47],[59,[55],[61]]]]]]
21 [17,[9,[5,[2,[0],[4]],[8]],[15,[13,[11,[10],[12]],[14]],[16]]],[40,[27,[21,[19,[18],[20]],[24,[22],[25]]],[28]],[44,[42,[41],[]],[51,[47],[59,[55],[61]]]]]] -> [17,[9,[5,[2,[0],[4]],[8]],[15,[13,[11,[10],[12]],[14]],[16]]],[40,[27,[19,[18],[21,[20],[24,[22],[25]]]],[28]],[44,[42,[41],[]],[51,[47],[59,[55],[61]]]]]]
1: có nghĩa là đối với bất kỳ nút nào, tất cả các khóa trong cây con bên trái sẽ nhỏ hơn khóa đó và tất cả các khóa trong cây con bên phải đều lớn hơn nó
2: để ngăn chặn liên kết, tôi đã nhúng chúng dưới dạng nhận xét
data B=B[B]Int
sẽ tiết kiệm thêm một số byte.