Subversion Repositories programming

Rev

Go to most recent revision | Details | Last modification | View Log | RSS feed

Rev Author Line No. Line
41 irasnyd 1
// Written by Ira Snyder
2
// Due Date: 11-24-2004
3
// Project #4
4
 
5
import java.io.*;
6
import java.util.*;
7
 
8
class AVLTree {
9
    private int key, height;
43 irasnyd 10
    private Object data;
41 irasnyd 11
    private AVLTree left, right;
12
 
13
    public static final AVLTree NIL = new AVLTree();
14
 
43 irasnyd 15
    public AVLTree( int key, Object data ) {
41 irasnyd 16
        this.key = key;
43 irasnyd 17
        this.data = data;
41 irasnyd 18
        left = right = NIL;
19
    }
20
 
43 irasnyd 21
    public boolean add( int key, Object data ) {
41 irasnyd 22
        int oldSize = size();
43 irasnyd 23
        grow(key,data);
41 irasnyd 24
        return size() > oldSize;
25
    }
26
 
43 irasnyd 27
    //provide name mapping
28
    public boolean insert( int key, Object data ) {
29
        return add(key,data);
30
    }
41 irasnyd 31
 
43 irasnyd 32
    public AVLTree grow( int key, Object data ) {
33
        if( this == NIL ) return new AVLTree(key,data);
34
        if( key == this.key ) { this.data = data; return this; } //prevent key dupes, update data
35
        if( key < this.key ) left = left.grow(key,data);
36
        else right = right.grow(key,data);
37
 
41 irasnyd 38
        rebalance();
39
 
40
        height = 1 + Math.max(left.height,right.height);
41
        return this;
42
    }
43
 
44
    public int size() {
45
        if( this == NIL ) return 0;
46
        return 1 + left.size() + right.size();
47
    }
48
 
42 irasnyd 49
    //I like the BinaryTree toString better than the author's toString()
50
    //so I used it here instead. I left the author's code for completeness.
51
    /*
41 irasnyd 52
    public String toString() {
53
        if( this == NIL ) return "";
54
        return left + " " + key + " " + right;
55
    }
42 irasnyd 56
    */
57
 
58
    public String toString() {
59
 
60
        if( this == NIL ) return "()";
61
 
62
        String sLeft = sLeft = left.toString();
63
        String sRight = sRight = right.toString();
64
        String answer = new String();
65
 
66
        //assemble the string to return
67
        answer = "(";
68
        if( !sLeft.equals("()") ) { answer += sLeft + ","; }
69
        answer += key;
70
        if( !sRight.equals("()") ) { answer += "," + sRight; }
71
        answer += ")";
72
 
73
        //return the assembled string
74
        return answer;
75
    }
76
 
41 irasnyd 77
    private AVLTree() { //construct the empty tree
78
        left = right = this;
79
        height = -1;
80
    }
81
 
43 irasnyd 82
    private AVLTree( int key, Object data, AVLTree left, AVLTree right ) {
41 irasnyd 83
        this.key = key;
43 irasnyd 84
        this.data = data;
41 irasnyd 85
        this.left = left;
86
        this.right = right;
87
        height = 1 + Math.max(left.height,right.height);
88
    }
89
 
90
    private void rebalance() {
91
        if( right.height > (left.height + 1) ) {
92
            if( right.left.height > right.right.height ) right.rotateRight();
93
            rotateLeft();
94
        }
95
        else if( left.height > (right.height + 1) ) {
96
            if( left.right.height > left.left.height ) left.rotateLeft();
97
            rotateRight();
98
        }
99
    }
100
 
101
    private void rotateLeft() {
43 irasnyd 102
        left = new AVLTree(key,data,left,right.left);
41 irasnyd 103
        key = right.key;
43 irasnyd 104
        data = right.data;
41 irasnyd 105
        right = right.right;
106
    }
107
 
108
    private void rotateRight() {
43 irasnyd 109
        right = new AVLTree(key,data,left.right,right);
41 irasnyd 110
        key = left.key;
43 irasnyd 111
        data = left.data;
41 irasnyd 112
        left = left.left;
113
    }
114
 
42 irasnyd 115
    // new functions from Prog. Probs PG 411
116
    public int getHeight() { return height; }
43 irasnyd 117
 
118
    public int getHeight( int key ) {
119
        if( this == NIL ) { return -1; }
120
        if( key == this.key ) { return getHeight(); }
121
        if( key < this.key ) { return left.getHeight(key); }
122
        return right.getHeight(key);
123
    }
42 irasnyd 124
 
125
    public AVLTree getLeft() { 
126
        if( this == NIL ) { return NIL; }
127
        return left;
128
    }
43 irasnyd 129
 
130
    public AVLTree getLeft( int key ) {
131
        if( this == NIL ) { return null; } //key not in tree
132
        if( key == this.key ) { return getLeft(); }
133
        if( key < this.key ) { return left.getLeft(key); }
134
        return right.getLeft(key);
135
    }
42 irasnyd 136
 
43 irasnyd 137
    public AVLTree getRight() {
42 irasnyd 138
        if( this == NIL ) { return NIL; }
139
        return right;
140
    }
43 irasnyd 141
 
142
    public AVLTree getRight( int key ) {
143
        if( this == NIL ) { return null; } //key not in tree
144
        if( key == this.key ) { return getRight(); }
145
        if( key < this.key ) { return left.getRight(key); }
146
        return right.getRight(key);
147
    }
42 irasnyd 148
 
43 irasnyd 149
    public int getRoot() { return key; }
150
    public int getKey() { return key; }
151
    public Object getData() { return data; }
42 irasnyd 152
 
153
    public boolean contains( int x ) { 
154
        if( this == NIL ) { return false; }
155
        if( key == x ) { return true; }
156
 
157
        return left.contains(x) || right.contains(x);
158
    }
159
 
43 irasnyd 160
    // I am guessing this returns the tree with x == key as the root,
161
    // since the book was not very specific
162
    public Object get( int key ) {
42 irasnyd 163
        if( this == NIL ) { return NIL; }
43 irasnyd 164
        if( key == this.key ) { return data; }
42 irasnyd 165
 
43 irasnyd 166
        if( key < this.key ) { return left.get(key); }
167
        return right.get(key);
42 irasnyd 168
    }
169
 
170
    public boolean equals( Object object ) { 
171
        if( !(object instanceof AVLTree) ) { return false; }
172
 
173
        AVLTree temp = (AVLTree)object; //make it typed
174
 
175
        boolean l=false, r=false;
176
 
177
        //check the left
178
        if( left == NIL && temp.left == NIL ) l = true;
179
        else l = left.equals(temp.left);
180
 
181
        //check the right
182
        if( right == NIL && temp.right == NIL ) r = true;
183
        else r = right.equals(temp.right);
184
 
185
        return (temp.key == key) && l && r;
186
    }
187
 
43 irasnyd 188
    public AVLTree( int[] keys, Object[] data ) { 
189
        this(keys[0],data[0]); //create a new tree
42 irasnyd 190
 
191
        //call add() for every element in the array
43 irasnyd 192
        for( int i=1; i < keys.length; i++ ) add(keys[i],data[i]);
42 irasnyd 193
    }
194
    /*
195
    public boolean remove( int key ) { 
196
        if( this == NIL ) { return false; }
197
        if( key < this.key ) { return left.remove(key); }
198
        if( key > this.key ) { return right.remove(key); }
199
 
43 irasnyd 200
        if( left == NIL && right == NIL ) { 
201
            //same as "this = NIL;"
202
            setThis(NIL);
203
 
204
            return true; 
205
        }
42 irasnyd 206
        if( left == NIL ) { 
43 irasnyd 207
            //same as "this = new AVLTree(right.key,right.left,right.right);"
208
            AVLTree temp = new AVLTree(right.key,right.data,right.left,right.right);
209
            setThis(temp);
210
 
42 irasnyd 211
            return true;
212
        }
213
        if( right == NIL ) {
43 irasnyd 214
            //same as "this = new AVLTree(left.key,left.left,left.right);"
215
            AVLTree temp = new AVLTree(left.key,left.data,left.left,left.right);
216
            setThis(temp);
217
 
42 irasnyd 218
            return true;
219
        }
43 irasnyd 220
        //same as "this = new AVLTree(deleteMinimum(right));
221
        AVLTree temp = new AVLTree( deleteMinimum(right) );
222
        setThis(temp);
223
 
42 irasnyd 224
        rebalance(); //fix the balance
225
        return true;
44 irasnyd 226
    } */
227
 
228
    public void ira_dm() {
229
        System.out.println( this );
230
        System.out.println( deleteMinimum( this ) );
42 irasnyd 231
    }
232
 
44 irasnyd 233
    public AVLTree deleteMinimum( AVLTree tree ) {
234
        if( tree == NIL ) { return NIL; }
235
        if( tree.left == NIL && tree.right == NIL ) { return NIL; }
236
        if( tree.left == NIL ) { 
237
            return new AVLTree(tree.right.key,tree.right.data,
238
                               tree.right.left,tree.right.right); 
42 irasnyd 239
        }
44 irasnyd 240
        return new AVLTree(tree.key,tree.data,deleteMinimum(tree.left),tree.right);
42 irasnyd 241
    }
43 irasnyd 242
 
44 irasnyd 243
 
43 irasnyd 244
    private void setThis( AVLTree that ) {
245
        this.key = that.key;
246
        this.data = that.data;
247
        this.height = that.height;
248
        this.left = that.left;
249
        this.right = that.right;
250
    }
42 irasnyd 251
 
43 irasnyd 252
    public static void printInOrder( AVLTree tree ) {
253
        Queue queue = new Queue();
254
        queue.enqueue(tree);
255
 
256
        while( !queue.isEmpty() ) {
257
            AVLTree temp = (AVLTree)queue.dequeue();
258
            System.out.print(temp.getKey());
259
            if( temp.getLeft() != NIL ) { queue.enqueue(temp.getLeft()); }
260
            if( temp.getRight() != NIL ) { queue.enqueue(temp.getRight()); }
261
        }
262
    }
263
 
264
    public static void printPreOrder( AVLTree tree ) {
265
        if( tree == NIL ) return;
266
 
267
        System.out.print(tree.getKey());
268
        AVLTree.printPreOrder( tree.getLeft() );
269
        AVLTree.printPreOrder( tree.getRight() );
270
    }
271
 
41 irasnyd 272
} //end AVLTree class
273