STRUKTUR DATA
PROGRAM TEKNOLOGI INFORMASI DAN ILMU
KOMPUTER
UNIVERSITAS BRAWIJAYA
BAB : AVL TREE
NAMA : RIZKY MUHAMMAD
NIM : 145150200111085
TANGGAL : 02/12/2015
ASISTEN : - DWI NOVI SETIAWAN
-MUHAMMAD SYAFIQ
A. DEFINISI MASALAH
B. SOURCE CODE
Node.java
1 package latihan_Bab10;
2 public class Node {
3 int data;
4 int tinggi;
5 Node pKiri;
6 Node pKanan;
7 Node pInduk;
8 public Node(int data, int tinggi, Node kiri, Node
kanan, Node induk) {
9 // TODO Auto-generated constructor stub
10 this.data=data;
11 this.tinggi=tinggi;
12 this.pKiri=kiri;
13 this.pKanan=kanan;
14 this.pInduk=induk;
15 }
16 }
AVLT1.java
1 package latihan_Bab10;
2 public class AVLT1 {
3 private Node root;
4 public AVLT1(){root = null;}
5 //cari dt di tree, mengembalikan true jika ditemukan
6 //dan false jika tidak
7 public void hapusNode(int dt) {
8 int sim=0;
9 int run=0;
10 Node del = root;
11 while (run==0){
12 if(dt == del.data){
13 if(del.pInduk==null){
14 hapusRoot(del);
15 }
16 else{
17 hapusNode(del, sim);
18 }
19 run=1;
20 }
21 else if(dt < del.data){
22 del = del.pKiri;
23 sim=0;
24 }
25 else{
26 del = del.pKanan;
27 sim=1;
28 }
29 }
30 }
31 public void hapusRoot(Node del) {
32 if(del.pKanan!=null){
33 if(del.pKanan.pKiri==null){
34 del.pKanan.pKiri=del.pKiri;
35 }
36 else{
37 Node temp1= del.pKanan.pKiri;
38 del.pKanan.pKiri=null;
39 while(temp1.pKiri!=null){
40 temp1=temp1.pKiri;
41 }
42 if(temp1.pKanan!=null){
43 Node temp1k= temp1.pKanan;
44 temp1.pKanan=del.pKanan;
45 temp1.pKiri=del.pKiri;
46 temp1.pInduk.pKanan=temp1k;
47 root=temp1;
48 }
49 else{
50 temp1.pKanan=del.pKanan;
51 temp1.pKiri=del.pKiri;
52 root=temp1;
53 }
54 }
55 }
56 else{
57 root=del.pKiri;
58 }
59 }
60 public void hapusNode(Node del,int sim) {
61 if(del.pKanan!=null){
62 if(del.pKanan.pKiri==null){
63 if(sim==0){
64 del.pInduk.pKiri=del.pKanan;
65 }
66 else if(sim==1){
67 del.pInduk.pKanan=del.pKanan;
68 }
69 }
70 else{
71 Node temp1= del.pKanan.pKiri;
72 del.pKanan.pKiri=null;
73 while(temp1.pKiri!=null){
74 temp1=temp1.pKiri;
75 }
76 if(temp1.pKanan!=null){
77 Node temp1k=temp1.pKanan;
78 temp1.pKanan=del.pKanan;
79 temp1.pKiri=del.pKiri;
80 temp1.pInduk.pKanan=temp1k;
81 if(sim==0){
82 del.pInduk.pKiri=temp1;
83 }
84 else if(sim==1){
85 del.pInduk.pKanan=temp1;
86 }
87 }
88 else{
89 temp1.pKanan=del.pKanan;
90 temp1.pKiri=del.pKiri;
91 if(sim==0){
92 del.pInduk.pKiri=temp1;
93 }
94 else{
95 del.pInduk.pKanan=temp1;
96 }
97 }
98 }
99 }
100 else{
101 if(sim==0){
102 del.pInduk.pKiri=del.pKiri;
103 }
104 else if(sim==1){
105 del.pInduk.pKanan=del.pKiri;
106 }
107 }
108 }
109 public boolean cariDt(int dt){
110 Node temp = root;
111 while(temp != null){
112 if(dt == temp.data) return true;
113 //cariDt subtree pKiri
114 else if(dt < temp.data) temp = temp.pKiri;
115 //cariDt subtree pKanan
116 else temp = temp.pKanan;
117 }
118 //dt tidak ditemukan
119 return false;
120 }
121 //sisip dt ke dalam tree, returns true if berhasil,
122 // false jika gagal
123 //tree diseimbangkan menggunakan algoritma AVL
124 public boolean sisipDt(int dt){
125 if(root == null){
126 //sisip dt di root
127 root = new Node(dt, 1, null, null, null);
128 return true;
129 }
130 //tree tidak kosong
131 else {
132 //mulai dari root
133 Node temp = root;
134 Node prev = null;
135 //cari lokasi penyisipan dt
136 while(temp != null){
137 if(dt == temp.data) {
138 return false;
139 }
140 //sisip dt di subtree pKiri
141 else if(dt < temp.data){
142 prev = temp;
143 temp = temp.pKiri;
144 }
145 //sisip dt di subtree pKanan
146 else {
147 prev = temp;
148 temp = temp.pKanan;
149 }
150 }
151 //buat node baru
152 temp = new Node(dt, 1, null, null, prev);
153 if(dt < prev.data){
154 prev.pKiri = temp;//sisip di pKiri
155
156 }
157 else{
158 prev.pKanan = temp; //sisipDt at pKanan
159 }
160 //Balancing
161 //mulai dari node yang disisipkan dan
162 //bergerak menuju root
163 balancing(temp);
164 //penyisipan berhasil
165 return true;
166 }
167 }
168 public void balancing(Node temp) {
169 while(temp != null){
170 //subtree pKiri dan pKanan memenuhi kondisi AVL
171 if(Math.abs(tinggi(temp.pKiri)-tinggi(temp.pKanan))<=1){
172 temp.tinggi = Math.max(tinggi(temp.pKiri),
tinggi(temp.pKanan)) +1;
173 }
174 //kasus 1 algoritma AVL
175 //putar kanan
176 else if(tinggi(temp.pKiri)-tinggi(temp.pKanan) >= 2 &&
tinggi(temp.pKiri.pKiri) >= tinggi(temp.pKiri.pKanan))
177 {
178 rotateRight(temp);
179 }
180 //case 2 algoritma AVl
181 //putar Kiri
182 else if(tinggi(temp.pKanan)-
tinggi(temp.pKiri)>= 2 && tinggi(temp.pKanan.pKanan) >=
tinggi(temp.pKanan.pKiri))
183 {
184 Node baru = temp;
185 rotateLeft(baru);
186 }
187 //kasus 3 dari algoritma AVL
188 //putar kiri putar kanan
189 else if(tinggi(temp.pKiri)-
tinggi(temp.pKanan)>= 2 && tinggi(temp.pKiri.pKanan) >=
tinggi(temp.pKiri.pKiri))
190 {
191 rotateLeftRight(temp);
192 }
193 //kasus 4 dari algoritma AVL
194 //putar kanan putar kiri
195 else if(tinggi(temp.pKanan)-
tinggi(temp.pKiri)>= 2 && tinggi(temp.pKanan.pKiri) >=
tinggi(temp.pKanan.pKanan))
196 {
197 rotateRightLeft(temp);
198 }
199 temp = temp.pInduk;
200 }
201 }
202 public void rotateLeft(Node temp) {
203 Node parent = temp.pInduk;
204 Node pKanan = temp.pKanan;
205 temp.pKanan = pKanan.pKiri;
206 if(temp.pKanan != null) {
207 temp.pKanan.pInduk = temp;
208 }
209 pKanan.pKiri = temp;
210 temp.pInduk = pKanan;
211 pKanan.pInduk = parent;
212 if(parent == null) {
213 root = pKanan;
214 }
215 else if(parent.pKanan == temp) {
216 parent.pKanan = pKanan;
217 }
218 else {
219 parent.pKiri = pKanan;
220 }
221 //hitung tinggi subtree pKanan
222 temp.tinggi = Math.max(tinggi(temp.pKiri),
tinggi(temp.pKanan)) +1;
223 temp = pKanan;
224 //hitung tinggi dari root
225 temp.tinggi = Math.max(tinggi(temp.pKiri),
tinggi(temp.pKanan)) +1;
226 //rotateLeft(temp);
227 }
228 public void rotateRight(Node temp){
229 Node parent = temp.pInduk;
230 Node pKiri = temp.pKiri;
231 temp.pKiri = pKiri.pKanan;
232
233 if(temp.pKiri != null) temp.pKiri.pInduk =
temp;
234 pKiri.pKanan = temp;
235 temp.pInduk = pKiri;
236 pKiri.pInduk = parent;
237 if(parent == null) root = pKiri;
238 else if(parent.pKiri==temp)parent.pKiri =
pKiri;
239 else parent.pKanan = pKiri;
240 //hitung tinggi subtree pKanan
241 temp.tinggi = Math.max(tinggi(temp.pKiri),
tinggi(temp.pKanan)) +1;
242 temp = pKiri;
243 //hitung tinggi dari root
244 temp.tinggi = Math.max(tinggi(temp.pKiri),
tinggi(temp.pKanan)) +1;
245 //rotateRight(temp);
246 }
247 public void rotateLeftRight(Node temp) {
248 Node parent = temp.pInduk;
249 Node pKiripKanan = temp.pKiri.pKanan;
250
251 temp.pKiri.pKanan = pKiripKanan.pKiri;
252 if(temp.pKiri.pKanan!= null){
253 temp.pKiri.pKanan.pInduk = temp.pKiri;
254 }
255 pKiripKanan.pKiri = temp.pKiri;
256 temp.pKiri.pInduk = pKiripKanan;
257 temp.pKiri = pKiripKanan.pKanan;
258 if(temp.pKiri != null){
259 temp.pKiri.pInduk = temp;
260 }
261 pKiripKanan.pKanan = temp;
262 temp.pInduk = pKiripKanan;
263 pKiripKanan.pInduk = parent;
264 if(parent == null) {
265 root = pKiripKanan;
266 }
267 else if(parent.pKiri==temp) {
268 parent.pKiri = pKiripKanan;
269 }
270 else{
271 parent.pKanan = pKiripKanan;
272 }
273 //hitung tinggi subtree pKanan
274 temp.tinggi = Math.max(tinggi(temp.pKiri),
tinggi(temp.pKanan)) +1;
275 temp = pKiripKanan;
276 //hitung tinggi dari root
277 temp.tinggi = Math.max(tinggi(temp.pKiri),
tinggi(temp.pKanan)) +1;
278 }
279 public void rotateRightLeft(Node temp) {
280 Node parent = temp.pInduk;
281 Node pKananpKiri = temp.pKanan.pKiri;
282 temp.pKanan.pKiri = pKananpKiri.pKanan;
283 if(temp.pKanan.pKiri!= null){
284 temp.pKanan.pKiri.pInduk = temp.pKanan;
285 }
286 pKananpKiri.pKanan = temp.pKanan;
287 temp.pKanan.pInduk = pKananpKiri;
288 temp.pKanan = pKananpKiri.pKiri;
289 if(temp.pKanan != null) {
290 temp.pKanan.pInduk = temp;
291 }
292 pKananpKiri.pKiri = temp;
293 temp.pInduk = pKananpKiri;
294 pKananpKiri.pInduk = parent;
295 if(parent == null) {
296 root = pKananpKiri;
297 }
298 else if(parent.pKanan == temp){
299 parent.pKanan = pKananpKiri;
230 }
231 else {
232 parent.pKiri = pKananpKiri;
233 }
234 temp.tinggi = Math.max(tinggi(temp.pKiri),
tinggi(temp.pKanan)) +1;
235 temp = pKananpKiri;
236 temp.tinggi = Math.max(tinggi(temp.pKiri),
tinggi(temp.pKanan)) +1;
237 }
238 public int tinggi(){
239 return root.tinggi;
240 }
241 private int tinggi(Node node){
242 if(node == null)return 0;
243 else return node.tinggi;
244 }
245 //hitung node-node dari tree
246 public int jumlahNode() {
247 return jumlahNode(root);
248 }
249 public void inOrderTraversal(){
250 inOrder(root);
251 }
252 private void inOrder(Node r){
253 if (r == null)return;
254 inOrder(r.pKiri);
255 System.out.printf("-%d",r.data);
256 inOrder(r.pKanan);
257 }
258 //hitung node-node dari tree
259 private int jumlahNode(Node node){
260 if(node == null) {
261 return 0;
262 }
263 else {
264 return 1 +jumlahNode(node.pKiri)
+jumlahNode(node.pKanan);
265 }
266
267 }
268 public static void main (String[] args) {
269 AVLT1 t = new AVLT1();
270 t.sisipDt(3);
271 t.inOrderTraversal();System.out.println();
272 t.sisipDt(4);
273 t.inOrderTraversal();System.out.println();
274 t.sisipDt(6);
275 t.inOrderTraversal();System.out.println();
276 t.sisipDt(5);
277 t.inOrderTraversal();System.out.println();
278 t.sisipDt(15);
279 t.inOrderTraversal();System.out.println();
280 t.sisipDt(10);
281 t.inOrderTraversal();System.out.println();
282 t.sisipDt(20);
283 t.inOrderTraversal();System.out.println();
284 t.sisipDt(17);
285 t.inOrderTraversal();System.out.println();
286 t.sisipDt(25);t.inOrderTraversal();System.out.println
();
287 System.out.println();
288 System.out.println("Hapus 25");
289 t.hapusNode(25);t.inOrderTraversal();System.out.println();
290 System.out.println("Hapus 3");
291 t.hapusNode(3);t.inOrderTraversal();System.out.println();
292 }
293 }
Method putarKiri
Method putarKanan
Method putarKananKiri
No. 1
Method hapusNode
No. 2
No. 3
AVL Tree
E. KESIMPULAN
AVL Tree adalah sebuah binary search tree yang mempunyai syarat bahwa setiap anak
kiri dan anak kanan hanya boleh mempunyai perbedaan tinggi maksimal satu. Sama seperti
BST, nilai yang diinsertkan atau disisipkan pada AVL tree jika nilai tersebut lebih kecil
dari pada induknya maka akan masuk ke anak kiri induk sedangkan jika nilai itu lebih besar
maka akan masuk ke sebelah kanan induk.
Perbedaan antara AVL dan BST adalah AVL mempunyai perbedaan tinggi maksimal
antara subtree kiri dan kanan maksimal 1, perbadaan lainnya adalah jika terjadi Worst Case
dari BST saat berntuk tree tidak balance, mengakibatkan operasi searching pada BST
menjadi O(n), tidak sebagaimana yang diharapkan yaitu O(log n). BST menggunakan lebih
sedikit memory dan melakukan proses yang lebih cepat dibanding dengan AVL tree.
Kegunaan dari AVL adalah seperi kegunaan dari tree sendiri yang berbeda hanyalah
syarat dari AVl tree. Penerapan nya antara lain diimplementasikan pada routing table pada
router, Data Compresion Code, diimplementasikan pada ekspresi parsers dan ekspresi
solvers, dan untuk menyelesaikan masalah pada database seperti halnya indexing.
Gambar Struktur data AVL adalah sebagai berikut