I am working on a project for my Data Structures class that asks me to write a class to implement a linked list of ints.
Use an inner class for the Node.
Include the methods below.
Write a tester to enable you to test all of the methods with whatever data you want in any order.
I have to create a method called "public void addToBack(int item)". This method is meant to "Add an Item to the end of the list" I have my code for this method down below. When I execute this method my list becomes empty. Does someone know what I did wrong and how to fix it?
import java.util.Random;
import java.util.Scanner;
public class LinkedListOfInts {
Node head;
Node tail;
private class Node {
int value;
Node nextNode;
public Node(int value, Node nextNode) {
this.value = value;
this.nextNode = nextNode;
}
}
public LinkedListOfInts(LinkedListOfInts other) {
Node tail = null;
for (Node n = other.head; n != null; n = n.nextNode) {
if (tail == null)
this.head = tail = new Node(n.value, null);
else {
tail.nextNode = new Node(n.value, null);
tail = tail.nextNode;
}
}
}
public LinkedListOfInts(int[] other) {
Node[] nodes = new Node[other.length];
for (int index = 0; index < other.length; index++) {
nodes[index] = new Node(other[index], null);
if (index > 0) {
nodes[index - 1].nextNode = nodes[index];
}
}
head = nodes[0];
}
public LinkedListOfInts(int N, int low, int high) {
Random random = new Random();
for (int i = 0; i < N; i++)
this.addToFront(random.nextInt(high - low) + low);
}
public void addToFront(int x) {
head = new Node(x, head);
}
public void addToBack(int x) {
if (head == null) {
head = new Node(x, head);
return;
}
tail = head;
while (tail.nextNode != null) {
tail = tail.nextNode;
}
tail.nextNode = new Node(x, tail);
}
public String toString() {
String result = "";
for (Node ptr = head; ptr != null; ptr = ptr.nextNode) {
if (!result.isEmpty()) {
result += ", ";
}
result += ptr.value;
}
return "[" + result + "]";
}
public static void main(String[] args) {
Scanner input = new Scanner(System.in);
LinkedListOfInts list = new LinkedListOfInts(10, 1, 20);
boolean done = false;
while (!done) {
System.out.println("1. Add to Back");
System.out.println("2. toString");
switch (input.nextInt()) {
case 1:
System.out.println("Add an Item to the Back of a List.");
list.addToBack(input.nextInt());
break;
case 2:
System.out.println("toString");
System.out.println(list.toString());
break;
}
}
}
}
When you add to the tail the nextNode should point to null
tail.nextNode = new Node(x, null);
At the moment you are having an endless loop
I'm trying to implement a generic binary search tree. I'm inserting 7 integers and want them to return with inOrder traversal however it's only returning 4 values out of order. Then I check if the tree contains a specific value but it always returns null and i'm unsure why. I'll post the code below, any idea's on why my output is what it is? I know my issues are probably within my insert and find methods, but unsure why, some clarification would be nice. Appreciate any advice, thanks!
Output when inserting integers 15, 10, 20, 5, 13, 11, 19:
run:
InOrder:
Inorder traversal: 10 15 11 19
Is 11 in the tree? null
BUILD SUCCESSFUL (total time: 0 seconds)
Node.class:
class Node<E> {
protected E element;
protected Node<E> left;
protected Node<E> right;
public Node(E e) {
element = e;
}
}
BinarySearchTree.class:
class BinarySearchTree<E extends Comparable<E>> {
private Node<E> root;
public BinarySearchTree() {
root = null;
}
public Node find(E e) {
Node<E> current = root;
while (e.compareTo(current.element) != 0) {
if (e.compareTo(current.element) < 0) {
current = current.left;
}
else {
current = current.right;
}
if (current == null) {
return null;
}
}
return current;
}
public void insert(E e) {
Node<E> newNode = new Node<>(e);
if (root == null) {
root = newNode;
} else {
Node<E> current = root;
Node<E> parent = null;
while (true) {
parent = current;
if (e.compareTo(current.element) < 0) {
current = current.left;
}
if (current == null) {
parent.left = newNode;
return;
} else {
current = current.right;
if (current == null) {
parent.right = newNode;
return;
}
}
}
}
}
public void traverse(int traverseType) {
switch(traverseType) {
case 1: System.out.print("\nPreorder traversal: ");
preOrder(root);
break;
case 2: System.out.print("\nInorder traversal: ");
inOrder(root);
break;
case 3: System.out.print("\nPostorder traversal: ");
postOrder(root);
break;
}
System.out.println();
}
private void inOrder(Node<E> localRoot) {
if (localRoot != null) {
inOrder(localRoot.left);
System.out.print(localRoot.element + " ");
inOrder(localRoot.right);
}
}
private void preOrder(Node<E> localRoot) {
if (localRoot != null) {
System.out.print(localRoot.element + " ");
preOrder(localRoot.left);
preOrder(localRoot.right);
}
}
private void postOrder(Node<E> localRoot) {
if (localRoot != null) {
postOrder(localRoot.left);
postOrder(localRoot.right);
System.out.print(localRoot.element + " ");
}
}
}
Main class:
public class BST_Test{
public static void main(String[] args) {
testInteger();
}
static void testInteger() {
BinarySearchTree<Integer> itree = new BinarySearchTree<>();
itree.insert(15);
itree.insert(10);
itree.insert(20);
itree.insert(5);
itree.insert(13);
itree.insert(11);
itree.insert(19);
// Traverse tree
System.out.print("InOrder: ");
itree.traverse(2);
// Search for an element
System.out.println("Is 11 in the tree? " + itree.find(11));
}
}
The cause is your poorly formatted code is hiding the fact your insert method is incorrect.
This if statement does not have an opening curly brace { (and subsequently the closing curly brace } since it compiles), so as a result only the subsequent statement is included in this if block:
if (e.compareTo(current.element) < 0)
current = current.left
This means the following is executed regardless of whether the condition above is true...
if (current == null) {
parent.left = newNode;
return;
} ...
... and as a result if current != null, your insertion will then proceed to the right:
... else {
current = current.right;
if (current == null) {
parent.right = newNode;
return;
}
}
In full your current erroneous code, when formatted/indented appropriately is:
public void insert(E e) {
Node<E> newNode = new Node<>(e);
if (root == null) {
root = newNode;
} else {
Node<E> current = root;
Node<E> parent = null;
while (true) {
parent = current;
if (e.compareTo(current.element) < 0) // missing { ...
current = current.left; // ... so only this is in the if block
if (current == null) {
parent.left = newNode;
return;
} else { // oops, this should be else to the e.compareTo(current.element) < 0 condition
current = current.right;
if (current == null) {
parent.right = newNode;
return;
}
}
}
}
}
Fixed code (assuming duplicates are allowed):
public void insert(E e) {
Node<E> newNode = new Node<>(e);
if (root == null) {
root = newNode;
} else {
Node<E> current = root;
Node<E> parent = null;
while (true) {
parent = current;
if (e.compareTo(current.element) < 0) {
current = current.left;
if (current == null) {
parent.left = newNode;
return;
}
} else {
current = current.right;
if (current == null) {
parent.right = newNode;
return;
}
}
}
}
}
Moral of the story: Keeping your code well-formatted and using curly braces for blocks will save you headaches.
I'm making a Doubly Linked List that allows you to insert at the front and rear, as well as deleting any node from the list as long as it exists. The problem is that it doesn't work and gives off and either gives off a NullPointerException or it just says That Integer does not exist even though it does exist.The code is:
public class Numbers {
Node head = null; //Head of the list
Node tail = null; //end of the doubly list
int size = 0;
public void FrontInsert(int data) {
Node n = new Node();
if (head == null) {
head = n;
} else {
n.prev = head;
head.next = n;
head = n;
}
size++;
}
public void RearInsert(int data) {
Node n = new Node();
if (head == null) {
head = n;
tail = n;
} else {
n.next = tail;
tail.prev = n;
tail = n;
}
size++;
}
public void Delete(int x) {
if (size == 0) {
System.out.println("The list is empty.");
}
if (head.data == x) {
head = head.next;
if (head != null) {
head.prev = null;
}
size--;
return;
}
tmp = head;
while (tmp != null && tmp.data != x) {
tmp = tmp.next;
}
if (tmp == null) {
System.out.println("That integer does not exist.");
return;
}
if (tmp.data == x) {
tmp.prev.next = tmp.next;
if (tmp.next != null) {
tmp.next.prev = tmp.prev;
}
}
size--;
}
public void printList() {
while (head != null) {
System.out.print(head.data + " ");
head = head.prev;
}
}
public static void main(String[] args) {
Numbers nu = new Numbers();
}
class Node {
Node prev;
Node next;
int data;
public void Node(int data) {
this.data = data;
next = null;
prev = null;
}
}
}
Try this and check output
public class Numbers {
Node head = null;
Node tail = null;
int size = 0;
public void FrontInsert(int data) {
Node n = new Node(data);
if (head == null) { // first insert
head = n;
tail = n;
} else {
n.next = head;
head.prev = n;
head = n;
}
size++;
}
public void RearInsert(int data) {
Node n = new Node(data);
if (head == null) {
head = n;
tail = n;
} else {
n.prev = tail;
tail.next = n;
tail = n;
}
size++;
}
public void Delete(int index) { // index is the position to be remove
if (size == 0) {
System.out.println("The list is empty."); return;
}else if(index < 0 || index > size -1){
System.out.println("Index outOf Bound."); return;
}
Node currentNode = head;
for(int i = 1; i <= index ; i++){
currentNode = currentNode.next;
}
//remove
if (index == 0) {
currentNode.next.prev = null;
head = currentNode.next;
} else if (index == size - 1) {
currentNode.prev.next = null;
tail = currentNode.prev;
} else {
if (currentNode.prev != null) // Ensure its not header
currentNode.prev.next = currentNode.next;
if (currentNode.next != null) // Ensure its not tail
currentNode.next.prev = currentNode.prev;
}
size--;
}
public void printList() {
Node tmp = head;
while (tmp != null) {
System.out.print(tmp.data + " ");
tmp = tmp.next;
}
System.out.println();
}
public static void main(String[] args) {
Numbers nu = new Numbers();
nu.FrontInsert(1);nu.printList();
nu.FrontInsert(2);nu.printList();
nu.RearInsert(3);nu.printList();
nu.FrontInsert(4);nu.printList();
nu.RearInsert(3);nu.printList();
nu.FrontInsert(4);nu.printList();
nu.RearInsert(3);nu.printList();
nu.RearInsert(3);nu.printList();
nu.FrontInsert(4);nu.printList();
System.out.println();
nu.Delete(4);
nu.printList();
}
class Node {
Node prev;
Node next;
int data;
public Node(int data) {
this.data = data;
next = null;
prev = null;
}
}
}
Well, your head and tail were mutually exclusive, i mean when you add something to the tail of the list, you were only giving one side reference not both side, you have to says
tail.next = n; n.prev = tail; and tail = n.
Here is a working code:
public class Numbers {
Node head = null; //Head of the list
Node tail = null; //end of the doubly list
int size = 0;
public void FrontInsert(int data) {
Node n = new Node(data);
if (head == null) {
head = n;
tail = head;
} else {
n.next = head;
head.prev = n;
head = n;
}
size++;
}
public void RearInsert(int data) {
Node n = new Node(data);
if (head == null) {
head = n;
tail = head;
} else {
n.next = null;
tail.next = n;
n.prev = tail;
tail = n;
}
size++;
}
#SuppressWarnings("null")
public void Delete(int x) {
if (size == 0) {
System.out.println("The list is empty.");
return;
}
if (head.data == x) {
head = head.next;
if (head != null) {
head.prev = null;
}
size--;
return;
}
Node tmp = head;
while (true) {
if(tmp == null)
break;
if(tmp.data == x)
break;
System.out.println(tmp.data);
tmp = tmp.next;
}
if (tmp == null) {
System.out.println("That integer does not exist.");
return;
}
if (tmp.data == x) {
tmp.prev.next = tmp.next;
if (tmp.next != null) {
tmp.next.prev = tmp.prev;
}
}
size--;
}
public void printList() {
while (head != null) {
System.out.print(head.data + " ");
head = head.next;
}
}
public static void main(String[] args) {
Numbers nu = new Numbers();
nu.FrontInsert(2);
nu.FrontInsert(3);
nu.FrontInsert(6);
nu.RearInsert(8);
nu.RearInsert(20);
nu.Delete(8);
nu.printList();
// System.out.println(nu.head.data + "data");
// System.out.println(nu.head.next.data + "data");
}
class Node {
Node prev;
Node next;
private int data;
public Node(int data) {
this.data = data;
next = null;
prev = null;
}
}
}
My task is to implement a circular linked list in java (ascending order) but the problem is that it is going in an infinite loop
I have created a class of Node in which i have define two elements.
public class Node {
public int element;
public Node next;
public class Node {
int element;
Node next;
}
}
Now in the second class of List i have made a insert function i have define a Node head=null in the start and create a new nNode .After that i am checking in the head section if head==null then the first element will be nNode. After inserting the first element i will compare the next element and the head element if the head element is greater than it will shift next and the new nNode will be the head. Since it is the circular linked list it is working but it is also going in an infinite loop.
This is the List class in which i have use the node class variables
public class List {
void insert(int e) {
Node nNode = new Node();
Node tNode = head;
nNode.element = e;
if (head == null)
head = nNode;
else if (head.element > e) {
nNode.next = head;
head=nNode;
} else {
Node pNode = head;
while (tNode.next != head && tNode.element <= e) {
pNode = tNode;
tNode = tNode.next;
}
pNode.next = nNode;
nNode.next = tNode;
tNode.next=head;
}
}
}
I have created on sample program for circular linkedlist which hold name and age of given element.
It has add(), remove() and sorbasedOnAge() (Sorting is implemented by first getting clone and convert it into simple linked list. Then use merge sort so that performance of O(nLogn) could be achieved.)
If you like it don't forget to press like button.
package com.ash.practice.tricky;
import java.util.Collections;
import java.util.LinkedList;
public class CircularLinkedList implements Cloneable{
Node start;
public Node getHead() {
return start;
}
CircularLinkedList setHead(Node startNode) {
start = startNode;
return this;
}
public void add(String name, int age) {
if(name==null) {
System.out.println("name must not be null.");
return;
}
if(start == null) {
Node node = new Node(name,age);
start = node;
node.next = start;
} else {
Node node = new Node(name,age);
Node temp = start;
while(temp.next != start) {
temp = temp.next;
}
temp.next = node;
node.next = start;
}
}
public CircularLinkedList clone()throws CloneNotSupportedException{
return (CircularLinkedList)super.clone();
}
public boolean remove(String name) {
if(name==null) {
return false;
} else if(start==null) {
return false;
} else if(start.getName().equals(name)) {
if(size()>1) {
Node temp = start;
while(temp.next!=start) {
temp = temp.next;
}
temp.next = start.next;
start = start.next;
} else {
start = null;
}
return true;
} else {
Node temp = start;
Node next = null;
Node prev = null;
while(temp.next != start) {
String currName = temp.name;
if(currName.equals(name)) {
next = temp.next;
break;
} else {
temp = temp.next;
}
}
if(next == null) {
return false;
}
prev = temp.next;
while(prev.next!=temp) {
prev = prev.next;
}
prev.next = next;
temp = null;
return true;
}
}
/*
public Node getPrevious(String name, int age) {
Node curr = new Node(name,age);
Node temp = curr;
while(temp.next!=curr) {
temp = temp.next;
}
return temp;
}
*/
public int size() {
int count = 1;
if(start != null) {
Node temp = start;
while(temp.next!=start) {
count++;
temp = temp.next;
}
} else return 0;
return count;
}
public int listSize() {
int count = 1;
if(start != null) {
Node temp = start;
while(temp.next!=null) {
count++;
temp = temp.next;
}
} else return 0;
return count;
}
public void display() {
if(start == null) {
System.out.println("No element present in list.");
} else {
Node temp = start;
while(temp.next != start) {
System.out.println(temp);
temp = temp.next;
}
System.out.println(temp);
}
}
public void displayList() {
if(start == null) {
System.out.println("No element present in list.");
} else {
Node temp = start;
while(temp.next != null) {
System.out.println(temp);
temp = temp.next;
}
System.out.println(temp);
}
}
public Node getPrevious(Node curr) {
if(curr==null) {
return null;
} else {
Node temp = curr;
while(temp.next!=curr) {
temp = temp.next;
}
return temp;
}
}
Node getMiddle() {
Node result = null;
Node temp = start.next;
result = start.next;
Node end = getPrevious(start);
end.next = null;
while(temp.next!=null) {
if(temp.next.next!=null) {
temp = temp.next.next;
result = result.next;
} else {
return result;
}
}
return result;
}
private static CircularLinkedList SortCollections(CircularLinkedList list) {
return SortCollections.doSortBasedOnAge(list);
}
private static class Node {
Node next;
String name;
int age;
Node(String name,int age) {
this.name = name;
this.age = age;
}
String getName() {
return name;
}
int getAge() {
return age;
}
public String toString() {
return "name = "+name +" : age = "+age;
}
#Override
public int hashCode() {
final int prime = 31;
int result = 1;
result = prime * result + age;
result = prime * result + ((name == null) ? 0 : name.hashCode());
return result;
}
#Override
public boolean equals(Object obj) {
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
Node other = (Node) obj;
if (age != other.age)
return false;
if (name == null) {
if (other.name != null)
return false;
} else if (!name.equals(other.name))
return false;
return true;
}
}
private static class SortCollections {
static Node mergeSort(Node head) {
if(head == null || head.next == null) {
return head;
}
Node middle = getMiddle(head);
Node nextHead = middle.next;
middle.next = null;
Node left = mergeSort(head);
Node right = mergeSort(nextHead);
Node sortedList = sortedMerged(left, right);
return sortedList;
}
public static CircularLinkedList doSortBasedOnAge(CircularLinkedList list) {
CircularLinkedList copy = null;
try {
copy = list.clone();
} catch (CloneNotSupportedException e) {
e.printStackTrace();
}
if(copy!=null) {
Node head = copy.getHead();
Node end = copy.getPrevious(head);
end.next = null;
Node startNode = mergeSort(head);
CircularLinkedList resultList = new CircularLinkedList().setHead(startNode);
return resultList;
} else {
System.out.println("copy is null");
}
return null;
}
private static Node sortedMerged(Node a, Node b) {
if(a == null) {
return b;
} else if(b == null) {
return a;
}
Node result = null;
if(a.getAge() > b.getAge()) {
result = b;
result.next = sortedMerged(a, b.next);
} else {
result = a;
result.next = sortedMerged(a.next, b);
}
return result;
}
private static Node getMiddle(Node head) {
Node result = null;
Node temp = head;
result = head;
while(temp.next!=null) {
if(temp.next.next!=null) {
temp = temp.next.next;
result = result.next;
} else {
return result;
}
}
return result;
}
}
public static void main(String[] args) {
CircularLinkedList list = new CircularLinkedList();
Collections.sort(new LinkedList());
list.add("ashish", 90);
list.add("rahul", 80);
list.add("deepak", 57);
list.add("ankit", 24);
list.add("raju", 45);
list.add("piyush", 78);
list.add("amit", 12);
//list.display();
/*System.out.println("---------------- size = "+list.size());
System.out.println(list.remove("deepak"));
//list.display();
System.out.println("---------------- size = "+list.size());
System.out.println(list.remove("ashish"));
//list.display();
System.out.println("---------------- size = "+list.size());
System.out.println(list.remove("raju"));
//list.display();
System.out.println("---------------- size = "+list.size());
list.add("aman", 23);
System.out.println("---------------- size = "+list.size());
list.display();
System.out.println("Previous Node of second node is : "+list.getPrevious(list.start.next));
System.out.println("Previous Node of start node is : "+list.getPrevious(list.start));
System.out.println("Previous Node of piyush node is : "+list.getPrevious("piyush",78));*/
list.display();
System.out.println("---------------- size = "+list.size());
//System.out.println(list.getMiddle());
CircularLinkedList newList = CircularLinkedList.SortCollections(list);
newList.displayList();
System.out.println("---------------- size = "+newList.listSize());
}
}
Let's consider the following situation:
The list contains elements B,C,X. Now you want to insert A and then Z.
void insert(int e) {
Node nNode = new Node(); //the new node, step 1: A, step2: Z
Node tNode = head; //step1: points to B, step2: points to A
nNode.element = e;
if (head == null) { //false in both steps
head = nNode;
head.next = head; //I added this line, otherwise you'd never get a circular list
} //don't forget the curly braces when adding more than one statement to a block
else if (head.element > e) { //true in step 1, false in step 2
nNode.next = head; //A.next = A
head=nNode; //A is the new head, but X.next will still be B
} else {
//you'll enter here when adding Z
Node pNode = head; //points to A because of step 1
//when tNode = X you'll start over at B, due to error in step 1
//the condition will never be false, since no node's next will point to A
//and no node's element is greater than Z
while (tNode.next != head && tNode.element <= e) {
pNode = tNode;
tNode = tNode.next;
}
//in contrast to my previous answer, where I had an error in my thought process,
//this is correct: the node is inserted between pNode and tNode
pNode.next = nNode;
nNode.next = tNode;
tNode.next=head; //delete this
}
}
As you can see, there are at least the following problems in your code:
tNode.next=head; is not necessary, since if you insert a node between pNode and tNode, tNode.next should not be affected (and if tNode is the last node, next should already point to the head, while in all other cases this assignment would be wrong).
In the two branches above, where you set head, you're not setting the next element of the last node to head. If you don't do this when adding the first node, that's not necessarily a problem, but leaving that out when adding a new head (second condition) you'll produce an incorrect state which then might result in endless loops
What you might want to do:
Remove the tNode.next=head; statement.
If you add a new head locate the last node and set the head as its next node. That means that if you have only one node, it references itself. If you add a node at the front (your second condition) you'll have to update the next reference of the last node, otherwise you'll get an endless loop if you try to add an element at the end.
After working two days on the code I finally solved it but this is not efficient code .
void insert(int e) {
Node nNode = new Node(); //the new node, step 1: A, step2: Z
Node tNode = head; //step1: points to B, step2: points to A
nNode.element = e;
if (head == null) { //false in both steps
head = nNode;
head.next = head;
}
else if (head.element > e) { //true in step 1, false in step 2
Node pNode = head;
pNode=tNode.next; //PNode is at head which will equal to tNode.next Which will be the next element
nNode.next = head;
head=nNode;
tNode.next.next=nNode; // Now I am moving the Tail Node next
} else {
Node pNode=head; //points to A because of step 1
while (tNode.next != head && tNode.element <= e) {
pNode = tNode;
tNode = tNode.next;
}
pNode.next = nNode;
nNode.next = tNode;
}
}
I am trying to implement BST algorithm using Cormen's pseudo code yet having issue.
Here is my Code for Node:
public class Node {
Node left;
Node right;
int value;
Node(int value){
this.value = value;
this.left = null;
this.right = null;
}
}
and for the Bstree:
public class Btree {
Node root;
Btree(){
this.root = null;
}
public static void inorderWalk(Node n){
if(n != null){
inorderWalk(n.left);
System.out.print(n.value + " ");
inorderWalk(n.right);
}
}
public static Node getParent(Btree t, Node n){
Node current = t.root;
Node parent = null;
while(true){
if (current == null)
return null;
if( current.value == n.value ){
break;
}
if (current.value > n.value){
parent = current;
current = current.left;
}
else{ //(current.value < n.value)
parent = current;
current = current.right;
}
}
return parent;
}
public static Node search(Node n,int key){
if(n == null || key == n.value ){
return n;
}
if(key < n.value){
return search(n.left,key);
}
else{
return search(n.right,key);
}
}
public static Node treeMinimum(Node x){
if(x == null){
return null;
}
while(x.left != null){
x = x.left;
}
return x;
}
public static Node treeMaximum(Node x){
if(x == null){
return null;
}
while(x.right != null){
x = x.right;
}
return x;
}
public static Node treeSuccessor(Btree t,Node x){
if (x.right == null){
return treeMinimum(x.right);
}
Node y = getParent(t,x);
while(y != null && x == y.right){
x = y;
y = getParent(t,y);
}
return y;
}
public static Btree insert(Btree t,Node z){
Node y = null;
Node x = t.root;
while(x != null){
y = x;
if(z.value < x.value)
x = x.left;
else
x = x.right;
}
Node tmp = getParent(t,z);
tmp = y;
if(y == null){
t.root = z;
}
else if(z.value < y.value)
y.left = z;
else
y.right = z;
return t;
}
public static Btree delete(Btree t,Node z){
Node y,x;
if (z.left == null || z.right == null)
y = z;
else
y = treeSuccessor(t,z);
if (y.left != null)
x = y.left;
else
x = y.right;
if (x != null){
Node tmp = getParent(t,x);
tmp = getParent(t,y);
}
if (getParent(t,y) == null ){
t.root = x;
}
else{
if( y == getParent(t,y).left ){
getParent(t,y).left = x;
}
else{
getParent(t,y).right = x;
}
}
if(y != z){
z.value = y.value;
}
return t;
}
public static void main(String[] args){
Btree test = new Btree();
Node n1 = new Node(6);
Node n2 = new Node(3);
Node n3 = new Node(9);
Node n4 = new Node(1);
Node n5 = new Node(16);
Node n6 = new Node(4);
Node n7 = new Node(2);
Node n8 = new Node(11);
Node n9 = new Node(13);
test = insert(test,n1);
test = insert(test,n2);
test = insert(test,n3);
test = insert(test,n4);
test = insert(test,n5);
test = insert(test,n6);
test = insert(test,n7);
test = insert(test,n8);
test = insert(test,n9);
inorderWalk(test.root);
System.out.println();
test = delete(test,n8);
inorderWalk(test.root);
System.out.println();
test = delete(test,n5);
inorderWalk(test.root);
System.out.println();
test = delete(test,n2);
inorderWalk(test.root);
System.out.println();
test = delete(test,n1);
inorderWalk(test.root);
}
}
The main problem is with the remove part, sometimes it is working as intended, sometimes removing wrongly and sometimes null pointer exception. What can be the issue ?
Ps: this is NOT a homework
Some immediate problems with your code: your treeSuccessor starts with
if (x.right == null){
return treeMinimum(x.right);
}
which should be if (x.right != null), of course.
Your insert code has the lines
Node tmp = getParent(t,z);
tmp = y;
where you assign to tmp and immediately assign to it again. It doesn't seem to me that you need these lines at all, since you don't use tmp further on. At this moment, you have y being the node to whose child z gets inserted, so just delete these lines.
Again, in delete, you have the lines
if (x != null){
Node tmp = getParent(t,x);
tmp = getParent(t,y);
}
where you don't actually do anything, since tmp is not visible outside this snippet. And further on, in delete, you repeat the expression getParent(t,y), which can be an expensive operation, so you should compute it only once and assign it to some variable.
But in general, your code, though it seems correct (probably apart from delete, which I did not understand completely but which looks suspicious), does not much resemble typical binary tree code. You don't really need the getParent and treeSuccessor methods to implement search, insert, and delete. The basic structure that you have for search works for the others too, with the following modifications:
with insert, when you get to a null link, instead of returning null, insert the element to that point
with delete, when you find the element, if it has only one (or no) child, replace it with that child, and if it has two children, replace it with either the maximum of the left child tree or the minimum of the right child tree
Both of these require in addition that you keep track of the parent node while descending into the tree, but that's the only modification you need to make to search. In particular, there is never any need to go upwards in the tree (which treeSuccessor will do).
First of all, your implementation got nothing to do with object orientation (except using objects). The insert and delete operations for example should operate ON the Tree.
Besides, I would recommend to implement the Node class as a static member of the Tree class.
public class Tree {
private Node root = null;
// remainder omitted
public boolean insert(int element) {
if (isEmpty()) {
root = new Node(element);
return true; // empty tree, Node could be inserted, return true
}
Node current = root; // start at root
Node parent; // the current Node's parent
do {
parent = current;
if (element < current.element) {
current = current.left; // go to left
} else if (element > current.element) {
current = current.right; // go to right
} else {
return false; // duplicates are NOT allowed, element could not be inserted -> return false
} while (current != null);
Node node = new Node(element);
if (element < current.element) {
parent.left = node;
} else {
parent.right = node;
}
return true; // node successfully inserted
}
public boolean isEmpty() {
return root == null;
}
private static class Node { // static member class
Node left = null;
Node right = null;
final int element;
Node(int element) {
this.element = element;
}
}
}
...what is up with your delete code? It doesn't make a lot of sense. I would consider rewriting it in a more logical way. Without the meaningless single-letter variable names. And add comments!
One possible algorithm is:
Get the parent of the node to delete
Get the right-most node of the left subtree, or the leftmost node of the right subtree
Remove the node to delete and replace it with the node you found
Rebalance the tree
...or, if you want to hack up this stuff so it's right, I'd start looking at the
if (x != null){
Node tmp = getParent(t,x);
tmp = getParent(t,y);
}
part, because that's clearly wrong.
I'll have to side with Anon and go for the rewrite. The null pointers come from your getParent function (which explicitly returns nulls along other things). So I would start there and fix the function(s) so that they return one thing and one thing only at the end of the function.
Here is the complete Implementation of Binary Search Tree In Java
insert,search,countNodes,traversal,delete,empty,maximum & minimum node,find parent node,print all leaf node, get level,get height, get depth,print left view, mirror view
import java.util.NoSuchElementException;
import java.util.Scanner;
import org.junit.experimental.max.MaxCore;
class BSTNode {
BSTNode left = null;
BSTNode rigth = null;
int data = 0;
public BSTNode() {
super();
}
public BSTNode(int data) {
this.left = null;
this.rigth = null;
this.data = data;
}
#Override
public String toString() {
return "BSTNode [left=" + left + ", rigth=" + rigth + ", data=" + data + "]";
}
}
class BinarySearchTree {
BSTNode root = null;
public BinarySearchTree() {
}
public void insert(int data) {
BSTNode node = new BSTNode(data);
if (root == null) {
root = node;
return;
}
BSTNode currentNode = root;
BSTNode parentNode = null;
while (true) {
parentNode = currentNode;
if (currentNode.data == data)
throw new IllegalArgumentException("Duplicates nodes note allowed in Binary Search Tree");
if (currentNode.data > data) {
currentNode = currentNode.left;
if (currentNode == null) {
parentNode.left = node;
return;
}
} else {
currentNode = currentNode.rigth;
if (currentNode == null) {
parentNode.rigth = node;
return;
}
}
}
}
public int countNodes() {
return countNodes(root);
}
private int countNodes(BSTNode node) {
if (node == null) {
return 0;
} else {
int count = 1;
count += countNodes(node.left);
count += countNodes(node.rigth);
return count;
}
}
public boolean searchNode(int data) {
if (empty())
return empty();
return searchNode(data, root);
}
public boolean searchNode(int data, BSTNode node) {
if (node != null) {
if (node.data == data)
return true;
else if (node.data > data)
return searchNode(data, node.left);
else if (node.data < data)
return searchNode(data, node.rigth);
}
return false;
}
public boolean delete(int data) {
if (empty())
throw new NoSuchElementException("Tree is Empty");
BSTNode currentNode = root;
BSTNode parentNode = root;
boolean isLeftChild = false;
while (currentNode.data != data) {
parentNode = currentNode;
if (currentNode.data > data) {
isLeftChild = true;
currentNode = currentNode.left;
} else if (currentNode.data < data) {
isLeftChild = false;
currentNode = currentNode.rigth;
}
if (currentNode == null)
return false;
}
// CASE 1: node with no child
if (currentNode.left == null && currentNode.rigth == null) {
if (currentNode == root)
root = null;
if (isLeftChild)
parentNode.left = null;
else
parentNode.rigth = null;
}
// CASE 2: if node with only one child
else if (currentNode.left != null && currentNode.rigth == null) {
if (root == currentNode) {
root = currentNode.left;
}
if (isLeftChild)
parentNode.left = currentNode.left;
else
parentNode.rigth = currentNode.left;
} else if (currentNode.rigth != null && currentNode.left == null) {
if (root == currentNode)
root = currentNode.rigth;
if (isLeftChild)
parentNode.left = currentNode.rigth;
else
parentNode.rigth = currentNode.rigth;
}
// CASE 3: node with two child
else if (currentNode.left != null && currentNode.rigth != null) {
// Now we have to find minimum element in rigth sub tree
// that is called successor
BSTNode successor = getSuccessor(currentNode);
if (currentNode == root)
root = successor;
if (isLeftChild)
parentNode.left = successor;
else
parentNode.rigth = successor;
successor.left = currentNode.left;
}
return true;
}
private BSTNode getSuccessor(BSTNode deleteNode) {
BSTNode successor = null;
BSTNode parentSuccessor = null;
BSTNode currentNode = deleteNode.left;
while (currentNode != null) {
parentSuccessor = successor;
successor = currentNode;
currentNode = currentNode.left;
}
if (successor != deleteNode.rigth) {
parentSuccessor.left = successor.left;
successor.rigth = deleteNode.rigth;
}
return successor;
}
public int nodeWithMinimumValue() {
return nodeWithMinimumValue(root);
}
private int nodeWithMinimumValue(BSTNode node) {
if (node.left != null)
return nodeWithMinimumValue(node.left);
return node.data;
}
public int nodewithMaximumValue() {
return nodewithMaximumValue(root);
}
private int nodewithMaximumValue(BSTNode node) {
if (node.rigth != null)
return nodewithMaximumValue(node.rigth);
return node.data;
}
public int parent(int data) {
return parent(root, data);
}
private int parent(BSTNode node, int data) {
if (empty())
throw new IllegalArgumentException("Empty");
if (root.data == data)
throw new IllegalArgumentException("No Parent node found");
BSTNode parent = null;
BSTNode current = node;
while (current.data != data) {
parent = current;
if (current.data > data)
current = current.left;
else
current = current.rigth;
if (current == null)
throw new IllegalArgumentException(data + " is not a node in tree");
}
return parent.data;
}
public int sibling(int data) {
return sibling(root, data);
}
private int sibling(BSTNode node, int data) {
if (empty())
throw new IllegalArgumentException("Empty");
if (root.data == data)
throw new IllegalArgumentException("No Parent node found");
BSTNode cureent = node;
BSTNode parent = null;
boolean isLeft = false;
while (cureent.data != data) {
parent = cureent;
if (cureent.data > data) {
cureent = cureent.left;
isLeft = true;
} else {
cureent = cureent.rigth;
isLeft = false;
}
if (cureent == null)
throw new IllegalArgumentException("No Parent node found");
}
if (isLeft) {
if (parent.rigth != null) {
return parent.rigth.data;
} else
throw new IllegalArgumentException("No Sibling is there");
} else {
if (parent.left != null)
return parent.left.data;
else
throw new IllegalArgumentException("No Sibling is there");
}
}
public void leafNodes() {
if (empty())
throw new IllegalArgumentException("Empty");
leafNode(root);
}
private void leafNode(BSTNode node) {
if (node == null)
return;
if (node.rigth == null && node.left == null)
System.out.print(node.data + " ");
leafNode(node.left);
leafNode(node.rigth);
}
public int level(int data) {
if (empty())
throw new IllegalArgumentException("Empty");
return level(root, data, 1);
}
private int level(BSTNode node, int data, int level) {
if (node == null)
return 0;
if (node.data == data)
return level;
int result = level(node.left, data, level + 1);
if (result != 0)
return result;
result = level(node.rigth, data, level + 1);
return result;
}
public int depth() {
return depth(root);
}
private int depth(BSTNode node) {
if (node == null)
return 0;
else
return 1 + Math.max(depth(node.left), depth(node.rigth));
}
public int height() {
return height(root);
}
private int height(BSTNode node) {
if (node == null)
return 0;
else
return 1 + Math.max(height(node.left), height(node.rigth));
}
public void leftView() {
leftView(root);
}
private void leftView(BSTNode node) {
if (node == null)
return;
int height = height(node);
for (int i = 1; i <= height; i++) {
printLeftView(node, i);
}
}
private boolean printLeftView(BSTNode node, int level) {
if (node == null)
return false;
if (level == 1) {
System.out.print(node.data + " ");
return true;
} else {
boolean left = printLeftView(node.left, level - 1);
if (left)
return true;
else
return printLeftView(node.rigth, level - 1);
}
}
public void mirroeView() {
BSTNode node = mirroeView(root);
preorder(node);
System.out.println();
inorder(node);
System.out.println();
postorder(node);
System.out.println();
}
private BSTNode mirroeView(BSTNode node) {
if (node == null || (node.left == null && node.rigth == null))
return node;
BSTNode temp = node.left;
node.left = node.rigth;
node.rigth = temp;
mirroeView(node.left);
mirroeView(node.rigth);
return node;
}
public void preorder() {
preorder(root);
}
private void preorder(BSTNode node) {
if (node != null) {
System.out.print(node.data + " ");
preorder(node.left);
preorder(node.rigth);
}
}
public void inorder() {
inorder(root);
}
private void inorder(BSTNode node) {
if (node != null) {
inorder(node.left);
System.out.print(node.data + " ");
inorder(node.rigth);
}
}
public void postorder() {
postorder(root);
}
private void postorder(BSTNode node) {
if (node != null) {
postorder(node.left);
postorder(node.rigth);
System.out.print(node.data + " ");
}
}
public boolean empty() {
return root == null;
}
}
public class BinarySearchTreeTest {
public static void main(String[] l) {
System.out.println("Weleome to Binary Search Tree");
Scanner scanner = new Scanner(System.in);
boolean yes = true;
BinarySearchTree tree = new BinarySearchTree();
do {
System.out.println("\n1. Insert");
System.out.println("2. Search Node");
System.out.println("3. Count Node");
System.out.println("4. Empty Status");
System.out.println("5. Delete Node");
System.out.println("6. Node with Minimum Value");
System.out.println("7. Node with Maximum Value");
System.out.println("8. Find Parent node");
System.out.println("9. Count no of links");
System.out.println("10. Get the sibling of any node");
System.out.println("11. Print all the leaf node");
System.out.println("12. Get the level of node");
System.out.println("13. Depth of the tree");
System.out.println("14. Height of Binary Tree");
System.out.println("15. Left View");
System.out.println("16. Mirror Image of Binary Tree");
System.out.println("Enter Your Choice :: ");
int choice = scanner.nextInt();
switch (choice) {
case 1:
try {
System.out.println("Enter Value");
tree.insert(scanner.nextInt());
} catch (Exception e) {
System.out.println(e.getMessage());
}
break;
case 2:
System.out.println("Enter the node");
System.out.println(tree.searchNode(scanner.nextInt()));
break;
case 3:
System.out.println(tree.countNodes());
break;
case 4:
System.out.println(tree.empty());
break;
case 5:
try {
System.out.println("Enter the node");
System.out.println(tree.delete(scanner.nextInt()));
} catch (Exception e) {
System.out.println(e.getMessage());
}
case 6:
try {
System.out.println(tree.nodeWithMinimumValue());
} catch (Exception e) {
System.out.println(e.getMessage());
}
break;
case 7:
try {
System.out.println(tree.nodewithMaximumValue());
} catch (Exception e) {
System.out.println(e.getMessage());
}
break;
case 8:
try {
System.out.println("Enter the node");
System.out.println(tree.parent(scanner.nextInt()));
} catch (Exception e) {
System.out.println(e.getMessage());
}
break;
case 9:
try {
System.out.println(tree.countNodes() - 1);
} catch (Exception e) {
System.out.println(e.getMessage());
}
break;
case 10:
try {
System.out.println("Enter the node");
System.out.println(tree.sibling(scanner.nextInt()));
} catch (Exception e) {
System.out.println(e.getMessage());
}
break;
case 11:
try {
tree.leafNodes();
} catch (Exception e) {
System.out.println(e.getMessage());
}
case 12:
try {
System.out.println("Enter the node");
System.out.println("Level is : " + tree.level(scanner.nextInt()));
} catch (Exception e) {
System.out.println(e.getMessage());
}
break;
case 13:
try {
System.out.println(tree.depth());
} catch (Exception e) {
System.out.println(e.getMessage());
}
break;
case 14:
try {
System.out.println(tree.height());
} catch (Exception e) {
System.out.println(e.getMessage());
}
break;
case 15:
try {
tree.leftView();
System.out.println();
} catch (Exception e) {
System.out.println(e.getMessage());
}
break;
case 16:
try {
tree.mirroeView();
} catch (Exception e) {
System.out.println(e.getMessage());
}
break;
default:
break;
}
tree.preorder();
System.out.println();
tree.inorder();
System.out.println();
tree.postorder();
} while (yes);
scanner.close();
}
}
As per my understanding following implementation done for binary search tree, kindly look
into that and let me know any feedback required
Insertion
InOrderTraversal
Search
Removal
Please take a look at the main method. so, Please provide your's feedback to improve further from my side.
public class BinarySearchTree {
private Node root;
public BinarySearchTree() {
root = null;
}
public BinarySearchTree(int rootData) {
root = new Node(rootData);
}
public void insertElement(int element,Node parent) {
Node temp = root;
if(parent!=null) temp = parent;
if(temp!=null) {
Node node = new Node(element);
if(element<temp.getData()) {
if(temp.getLeft()!=null)
insertElement(element, temp.getLeft());
else
temp.setLeft(node);
}else if(element>temp.getData()) {
if(temp.getRight()!=null)
insertElement(element, temp.getRight());
else
temp.setRight(node);
}
}
}
public void traverseInOrder() {
if(root!=null) {
traverse(root.getLeft());
System.out.println(root.getData());
traverse(root.getRight());
}
}
public void traverse(Node temp) {
if(temp!=null) {
traverse(temp.getLeft());
System.out.println(temp.getData());
traverse(temp.getRight());
}
}
public int searchElement(int element,Node node) {
Node temp = root;
if(node!=null) temp = node;
if(temp!=null) {
if(temp.getData()<element) {
if(temp.getRight()!=null)
return searchElement(element, temp.getRight());
}else if(temp.getData()>element) {
if(temp.getLeft()!=null)
return searchElement(element,temp.getLeft());
}else if(temp.getData()==element){
return temp.getData();
}
}
return -1;
}
public void remove(int element,Node node,Node predecer) {
Node temp = root;
if(node!=null) temp = node;
if(temp!=null) {
if(temp.getData()>element) {
remove(element, temp.getLeft(), temp);
}else if(temp.getData()<element) {
remove(element, temp.getRight(), temp);
}else if(element==temp.getData()) {
if(temp.getLeft()==null && temp.getRight()==null) {
if(predecer.getData()>temp.getData()) {
predecer.setLeft(null);
}else if(predecer.getData()<temp.getData()) {
predecer.setRight(null);
}
}else if(temp.getLeft()!=null && temp.getRight()==null) {
predecer.setRight(temp.getLeft());
}else if(temp.getLeft()==null && temp.getRight()!=null) {
predecer.setLeft(temp.getRight());
}else if(temp.getLeft()!=null && temp.getRight()!=null) {
Node leftMostElement = findMaximumLeft(temp.getLeft());
if(leftMostElement!=null) {
remove(leftMostElement.getData(), temp, temp);
temp.setData(leftMostElement.getData());
}
}
}
}
}
public Node findMaximumLeft(Node parent) {
Node temp = parent;
if(temp.getRight()!=null)
return findMaximumLeft(temp.getRight());
else
return temp;
}
public static void main(String[] args) {
BinarySearchTree bs = new BinarySearchTree(10);
bs.insertElement(29, null);
bs.insertElement(19, null);
bs.insertElement(209, null);
bs.insertElement(6, null);
bs.insertElement(7, null);
bs.insertElement(17, null);
bs.insertElement(37, null);
bs.insertElement(67, null);
bs.insertElement(-7, null);
bs.remove(6, null, null);
bs.traverseInOrder();}}