mirror of
https://github.com/TheAlgorithms/Java.git
synced 2025-07-25 13:34:54 +08:00
Formatted with Google Java Formatter
This commit is contained in:
@ -1,63 +1,65 @@
|
||||
package DataStructures.Lists;
|
||||
|
||||
public class CircleLinkedList<E> {
|
||||
private static class Node<E> {
|
||||
Node<E> next;
|
||||
E value;
|
||||
private static class Node<E> {
|
||||
Node<E> next;
|
||||
E value;
|
||||
|
||||
private Node(E value, Node<E> next) {
|
||||
this.value = value;
|
||||
this.next = next;
|
||||
}
|
||||
private Node(E value, Node<E> next) {
|
||||
this.value = value;
|
||||
this.next = next;
|
||||
}
|
||||
}
|
||||
|
||||
//For better O.O design this should be private allows for better black box design
|
||||
private int size;
|
||||
//this will point to dummy node;
|
||||
private Node<E> head = null;
|
||||
// For better O.O design this should be private allows for better black box design
|
||||
private int size;
|
||||
// this will point to dummy node;
|
||||
private Node<E> head = null;
|
||||
|
||||
//constructer for class.. here we will make a dummy node for circly linked list implementation with reduced error catching as our list will never be empty;
|
||||
public CircleLinkedList() {
|
||||
//creation of the dummy node
|
||||
head = new Node<E>(null, head);
|
||||
size = 0;
|
||||
// constructer for class.. here we will make a dummy node for circly linked list implementation
|
||||
// with reduced error catching as our list will never be empty;
|
||||
public CircleLinkedList() {
|
||||
// creation of the dummy node
|
||||
head = new Node<E>(null, head);
|
||||
size = 0;
|
||||
}
|
||||
|
||||
// getter for the size... needed because size is private.
|
||||
public int getSize() {
|
||||
return size;
|
||||
}
|
||||
|
||||
// for the sake of simplistiy this class will only contain the append function or addLast other
|
||||
// add functions can be implemented however this is the basses of them all really.
|
||||
public void append(E value) {
|
||||
if (value == null) {
|
||||
// we do not want to add null elements to the list.
|
||||
throw new NullPointerException("Cannot add null element to the list");
|
||||
}
|
||||
// head.next points to the last element;
|
||||
head.next = new Node<E>(value, head);
|
||||
size++;
|
||||
}
|
||||
|
||||
// getter for the size... needed because size is private.
|
||||
public int getSize() {
|
||||
return size;
|
||||
public E remove(int pos) {
|
||||
if (pos > size || pos < 0) {
|
||||
// catching errors
|
||||
throw new IndexOutOfBoundsException("position cannot be greater than size or negative");
|
||||
}
|
||||
|
||||
// for the sake of simplistiy this class will only contain the append function or addLast other add functions can be implemented however this is the basses of them all really.
|
||||
public void append(E value) {
|
||||
if (value == null) {
|
||||
// we do not want to add null elements to the list.
|
||||
throw new NullPointerException("Cannot add null element to the list");
|
||||
}
|
||||
//head.next points to the last element;
|
||||
head.next = new Node<E>(value, head);
|
||||
size++;
|
||||
// we need to keep track of the element before the element we want to remove we can see why
|
||||
// bellow.
|
||||
Node<E> before = head;
|
||||
for (int i = 1; i <= pos; i++) {
|
||||
before = before.next;
|
||||
}
|
||||
|
||||
public E remove(int pos) {
|
||||
if (pos > size || pos < 0) {
|
||||
//catching errors
|
||||
throw new IndexOutOfBoundsException("position cannot be greater than size or negative");
|
||||
}
|
||||
//we need to keep track of the element before the element we want to remove we can see why bellow.
|
||||
Node<E> before = head;
|
||||
for (int i = 1; i <= pos; i++) {
|
||||
before = before.next;
|
||||
}
|
||||
Node<E> destroy = before.next;
|
||||
E saved = destroy.value;
|
||||
// assigning the next reference to the the element following the element we want to remove... the last element will be assigned to the head.
|
||||
before.next = before.next.next;
|
||||
// scrubbing
|
||||
destroy = null;
|
||||
size--;
|
||||
return saved;
|
||||
|
||||
}
|
||||
|
||||
Node<E> destroy = before.next;
|
||||
E saved = destroy.value;
|
||||
// assigning the next reference to the the element following the element we want to remove...
|
||||
// the last element will be assigned to the head.
|
||||
before.next = before.next.next;
|
||||
// scrubbing
|
||||
destroy = null;
|
||||
size--;
|
||||
return saved;
|
||||
}
|
||||
}
|
||||
|
@ -1,26 +1,26 @@
|
||||
package DataStructures.Lists;
|
||||
|
||||
public class CountSinglyLinkedListRecursion extends SinglyLinkedList {
|
||||
public static void main(String[] args) {
|
||||
CountSinglyLinkedListRecursion list = new CountSinglyLinkedListRecursion();
|
||||
for (int i = 1; i <= 5; ++i) {
|
||||
list.insert(i);
|
||||
}
|
||||
assert list.count() == 5;
|
||||
public static void main(String[] args) {
|
||||
CountSinglyLinkedListRecursion list = new CountSinglyLinkedListRecursion();
|
||||
for (int i = 1; i <= 5; ++i) {
|
||||
list.insert(i);
|
||||
}
|
||||
assert list.count() == 5;
|
||||
}
|
||||
|
||||
/**
|
||||
* Calculate the count of the list manually using recursion.
|
||||
*
|
||||
* @param head head of the list.
|
||||
* @return count of the list.
|
||||
*/
|
||||
private int countRecursion(Node head) {
|
||||
return head == null ? 0 : 1 + countRecursion(head.next);
|
||||
}
|
||||
/**
|
||||
* Calculate the count of the list manually using recursion.
|
||||
*
|
||||
* @param head head of the list.
|
||||
* @return count of the list.
|
||||
*/
|
||||
private int countRecursion(Node head) {
|
||||
return head == null ? 0 : 1 + countRecursion(head.next);
|
||||
}
|
||||
|
||||
@Override
|
||||
public int count() {
|
||||
return countRecursion(getHead());
|
||||
}
|
||||
@Override
|
||||
public int count() {
|
||||
return countRecursion(getHead());
|
||||
}
|
||||
}
|
||||
|
@ -4,213 +4,185 @@ import java.util.Objects;
|
||||
|
||||
public class CursorLinkedList<T> {
|
||||
|
||||
|
||||
private static class Node<T> {
|
||||
private static class Node<T> {
|
||||
|
||||
T element;
|
||||
int next;
|
||||
T element;
|
||||
int next;
|
||||
|
||||
Node(T element, int next) {
|
||||
this.element = element;
|
||||
this.next = next;
|
||||
}
|
||||
Node(T element, int next) {
|
||||
this.element = element;
|
||||
this.next = next;
|
||||
}
|
||||
}
|
||||
|
||||
private final int os;
|
||||
private int head;
|
||||
private final Node<T>[] cursorSpace;
|
||||
private int count;
|
||||
private static final int CURSOR_SPACE_SIZE = 100;
|
||||
|
||||
{
|
||||
// init at loading time
|
||||
cursorSpace = new Node[CURSOR_SPACE_SIZE];
|
||||
for (int i = 0; i < CURSOR_SPACE_SIZE; i++) {
|
||||
cursorSpace[i] = new Node<>(null, i + 1);
|
||||
}
|
||||
cursorSpace[CURSOR_SPACE_SIZE - 1].next = 0;
|
||||
}
|
||||
|
||||
public CursorLinkedList() {
|
||||
os = 0;
|
||||
count = 0;
|
||||
head = -1;
|
||||
}
|
||||
|
||||
public void printList() {
|
||||
|
||||
if (head != -1) {
|
||||
|
||||
int start = head;
|
||||
while (start != -1) {
|
||||
|
||||
T element = cursorSpace[start].element;
|
||||
System.out.println(element.toString());
|
||||
start = cursorSpace[start].next;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the logical index of the element within the list , not the actual index of the
|
||||
* [cursorSpace] array
|
||||
*/
|
||||
public int indexOf(T element) {
|
||||
|
||||
Objects.requireNonNull(element);
|
||||
Node<T> iterator = cursorSpace[head];
|
||||
for (int i = 0; i < count; i++) {
|
||||
if (iterator.element.equals(element)) {
|
||||
return i;
|
||||
}
|
||||
iterator = cursorSpace[iterator.next];
|
||||
}
|
||||
|
||||
private final int os;
|
||||
private int head;
|
||||
private final Node<T>[] cursorSpace;
|
||||
private int count;
|
||||
private final static int CURSOR_SPACE_SIZE = 100;
|
||||
return -1;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param position , the logical index of the element , not the actual one within the
|
||||
* [cursorSpace] array . this method should be used to get the index give by indexOf() method.
|
||||
* @return
|
||||
*/
|
||||
public T get(int position) {
|
||||
|
||||
|
||||
{
|
||||
// init at loading time
|
||||
cursorSpace = new Node[CURSOR_SPACE_SIZE];
|
||||
for (int i = 0; i < CURSOR_SPACE_SIZE; i++) {
|
||||
cursorSpace[i] = new Node<>(null, i + 1);
|
||||
}
|
||||
cursorSpace[CURSOR_SPACE_SIZE - 1].next = 0;
|
||||
}
|
||||
if (position >= 0 && position < count) {
|
||||
|
||||
int start = head;
|
||||
int counter = 0;
|
||||
while (start != -1) {
|
||||
|
||||
public CursorLinkedList() {
|
||||
os = 0;
|
||||
count = 0;
|
||||
head = -1;
|
||||
}
|
||||
|
||||
public void printList() {
|
||||
|
||||
if (head != -1) {
|
||||
|
||||
|
||||
int start = head;
|
||||
while (start != -1) {
|
||||
|
||||
T element = cursorSpace[start].element;
|
||||
System.out.println(element.toString());
|
||||
start = cursorSpace[start].next;
|
||||
}
|
||||
T element = cursorSpace[start].element;
|
||||
if (counter == position) {
|
||||
return element;
|
||||
}
|
||||
|
||||
start = cursorSpace[start].next;
|
||||
counter++;
|
||||
}
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the logical index of the element within the list , not the actual
|
||||
* index of the [cursorSpace] array
|
||||
*/
|
||||
public int indexOf(T element) {
|
||||
public void removeByIndex(int index) {
|
||||
|
||||
if (index >= 0 && index < count) {
|
||||
|
||||
Objects.requireNonNull(element);
|
||||
Node<T> iterator = cursorSpace[head];
|
||||
for (int i = 0; i < count; i++) {
|
||||
if (iterator.element.equals(element)) {
|
||||
return i;
|
||||
}
|
||||
iterator = cursorSpace[iterator.next];
|
||||
T element = get(index);
|
||||
remove(element);
|
||||
}
|
||||
}
|
||||
|
||||
public void remove(T element) {
|
||||
|
||||
Objects.requireNonNull(element);
|
||||
|
||||
// case element is in the head
|
||||
T temp_element = cursorSpace[head].element;
|
||||
int temp_next = cursorSpace[head].next;
|
||||
if (temp_element.equals(element)) {
|
||||
free(head);
|
||||
head = temp_next;
|
||||
} else { // otherwise cases
|
||||
|
||||
int prev_index = head;
|
||||
int current_index = cursorSpace[prev_index].next;
|
||||
|
||||
while (current_index != -1) {
|
||||
|
||||
T current_element = cursorSpace[current_index].element;
|
||||
if (current_element.equals(element)) {
|
||||
cursorSpace[prev_index].next = cursorSpace[current_index].next;
|
||||
free(current_index);
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
return -1;
|
||||
prev_index = current_index;
|
||||
current_index = cursorSpace[prev_index].next;
|
||||
}
|
||||
}
|
||||
|
||||
count--;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param position , the logical index of the element , not the actual one
|
||||
* within the [cursorSpace] array .
|
||||
* this method should be used to get the index give by indexOf() method.
|
||||
* @return
|
||||
*/
|
||||
private void free(int index) {
|
||||
|
||||
public T get(int position) {
|
||||
Node os_node = cursorSpace[os];
|
||||
int os_next = os_node.next;
|
||||
cursorSpace[os].next = index;
|
||||
cursorSpace[index].element = null;
|
||||
cursorSpace[index].next = os_next;
|
||||
}
|
||||
|
||||
if (position >= 0 && position < count) {
|
||||
public void append(T element) {
|
||||
|
||||
int start = head;
|
||||
int counter = 0;
|
||||
while (start != -1) {
|
||||
Objects.requireNonNull(element);
|
||||
int availableIndex = alloc();
|
||||
cursorSpace[availableIndex].element = element;
|
||||
|
||||
T element = cursorSpace[start].element;
|
||||
if (counter == position) {
|
||||
return element;
|
||||
}
|
||||
|
||||
start = cursorSpace[start].next;
|
||||
counter++;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
return null;
|
||||
if (head == -1) {
|
||||
head = availableIndex;
|
||||
}
|
||||
|
||||
|
||||
public void removeByIndex(int index) {
|
||||
|
||||
if (index >= 0 && index < count) {
|
||||
|
||||
T element = get(index);
|
||||
remove(element);
|
||||
}
|
||||
|
||||
int iterator = head;
|
||||
while (cursorSpace[iterator].next != -1) {
|
||||
iterator = cursorSpace[iterator].next;
|
||||
}
|
||||
|
||||
public void remove(T element) {
|
||||
cursorSpace[iterator].next = availableIndex;
|
||||
cursorSpace[availableIndex].next = -1;
|
||||
|
||||
count++;
|
||||
}
|
||||
|
||||
Objects.requireNonNull(element);
|
||||
/** @return the index of the next available node */
|
||||
private int alloc() {
|
||||
|
||||
// case element is in the head
|
||||
T temp_element = cursorSpace[head].element;
|
||||
int temp_next = cursorSpace[head].next;
|
||||
if (temp_element.equals(element)) {
|
||||
free(head);
|
||||
head = temp_next;
|
||||
} else { // otherwise cases
|
||||
|
||||
int prev_index = head;
|
||||
int current_index = cursorSpace[prev_index].next;
|
||||
|
||||
while (current_index != -1) {
|
||||
|
||||
T current_element = cursorSpace[current_index].element;
|
||||
if (current_element.equals(element)) {
|
||||
cursorSpace[prev_index].next = cursorSpace[current_index].next;
|
||||
free(current_index);
|
||||
break;
|
||||
}
|
||||
|
||||
prev_index = current_index;
|
||||
current_index = cursorSpace[prev_index].next;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
count--;
|
||||
// 1- get the index at which the os is pointing
|
||||
int availableNodeIndex = cursorSpace[os].next;
|
||||
|
||||
if (availableNodeIndex == 0) {
|
||||
throw new OutOfMemoryError();
|
||||
}
|
||||
|
||||
private void free(int index) {
|
||||
|
||||
Node os_node = cursorSpace[os];
|
||||
int os_next = os_node.next;
|
||||
cursorSpace[os].next = index;
|
||||
cursorSpace[index].element = null;
|
||||
cursorSpace[index].next = os_next;
|
||||
|
||||
}
|
||||
|
||||
|
||||
public void append(T element) {
|
||||
|
||||
Objects.requireNonNull(element);
|
||||
int availableIndex = alloc();
|
||||
cursorSpace[availableIndex].element = element;
|
||||
|
||||
if (head == -1) {
|
||||
head = availableIndex;
|
||||
}
|
||||
|
||||
int iterator = head;
|
||||
while (cursorSpace[iterator].next != -1) {
|
||||
iterator = cursorSpace[iterator].next;
|
||||
}
|
||||
|
||||
cursorSpace[iterator].next = availableIndex;
|
||||
cursorSpace[availableIndex].next = -1;
|
||||
|
||||
|
||||
count++;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the index of the next available node
|
||||
*/
|
||||
private int alloc() {
|
||||
|
||||
|
||||
//1- get the index at which the os is pointing
|
||||
int availableNodeIndex = cursorSpace[os].next;
|
||||
|
||||
if (availableNodeIndex == 0) {
|
||||
throw new OutOfMemoryError();
|
||||
}
|
||||
|
||||
//2- make the os point to the next of the @var{availableNodeIndex}
|
||||
int availableNext = cursorSpace[availableNodeIndex].next;
|
||||
cursorSpace[os].next = availableNext;
|
||||
|
||||
// this to indicate an end of the list , helpful at testing since any err
|
||||
// would throw an outOfBoundException
|
||||
cursorSpace[availableNodeIndex].next = -1;
|
||||
|
||||
return availableNodeIndex;
|
||||
|
||||
}
|
||||
// 2- make the os point to the next of the @var{availableNodeIndex}
|
||||
int availableNext = cursorSpace[availableNodeIndex].next;
|
||||
cursorSpace[os].next = availableNext;
|
||||
|
||||
// this to indicate an end of the list , helpful at testing since any err
|
||||
// would throw an outOfBoundException
|
||||
cursorSpace[availableNodeIndex].next = -1;
|
||||
|
||||
return availableNodeIndex;
|
||||
}
|
||||
}
|
||||
|
@ -1,343 +1,307 @@
|
||||
package DataStructures.Lists;
|
||||
|
||||
/**
|
||||
* This class implements a DoublyLinkedList. This is done using the classes
|
||||
* LinkedList and Link.
|
||||
* <p>
|
||||
* A linked list is similar to an array, it holds values. However,
|
||||
* links in a linked list do not have indexes. With a linked list
|
||||
* you do not need to predetermine it's size as it grows and shrinks
|
||||
* as it is edited. This is an example of a double ended, doubly
|
||||
* linked list. Each link references the next link and the previous
|
||||
* one.
|
||||
* This class implements a DoublyLinkedList. This is done using the classes LinkedList and Link.
|
||||
*
|
||||
* <p>A linked list is similar to an array, it holds values. However, links in a linked list do not
|
||||
* have indexes. With a linked list you do not need to predetermine it's size as it grows and
|
||||
* shrinks as it is edited. This is an example of a double ended, doubly linked list. Each link
|
||||
* references the next link and the previous one.
|
||||
*
|
||||
* @author Unknown
|
||||
*/
|
||||
|
||||
public class DoublyLinkedList {
|
||||
/**
|
||||
* Head refers to the front of the list
|
||||
*/
|
||||
private Link head;
|
||||
/**
|
||||
* Tail refers to the back of the list
|
||||
*/
|
||||
private Link tail;
|
||||
/** Head refers to the front of the list */
|
||||
private Link head;
|
||||
/** Tail refers to the back of the list */
|
||||
private Link tail;
|
||||
|
||||
/**
|
||||
* Size refers to the number of elements present in the list
|
||||
*/
|
||||
private int size;
|
||||
/** Size refers to the number of elements present in the list */
|
||||
private int size;
|
||||
|
||||
/**
|
||||
* Default Constructor
|
||||
*/
|
||||
public DoublyLinkedList() {
|
||||
head = null;
|
||||
tail = null;
|
||||
size = 0;
|
||||
/** Default Constructor */
|
||||
public DoublyLinkedList() {
|
||||
head = null;
|
||||
tail = null;
|
||||
size = 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Constructs a list containing the elements of the array
|
||||
*
|
||||
* @param array the array whose elements are to be placed into this list
|
||||
* @throws NullPointerException if the specified collection is null
|
||||
*/
|
||||
public DoublyLinkedList(int[] array) {
|
||||
if (array == null) throw new NullPointerException();
|
||||
for (int i : array) {
|
||||
insertTail(i);
|
||||
}
|
||||
size = array.length;
|
||||
}
|
||||
|
||||
/**
|
||||
* Constructs a list containing the elements of the array
|
||||
*
|
||||
* @param array the array whose elements are to be placed into this list
|
||||
* @throws NullPointerException if the specified collection is null
|
||||
*/
|
||||
public DoublyLinkedList(int[] array) {
|
||||
if (array == null) throw new NullPointerException();
|
||||
for (int i : array) {
|
||||
insertTail(i);
|
||||
}
|
||||
size = array.length;
|
||||
/**
|
||||
* Insert an element at the head
|
||||
*
|
||||
* @param x Element to be inserted
|
||||
*/
|
||||
public void insertHead(int x) {
|
||||
Link newLink = new Link(x); // Create a new link with a value attached to it
|
||||
if (isEmpty()) // Set the first element added to be the tail
|
||||
tail = newLink;
|
||||
else head.previous = newLink; // newLink <-- currenthead(head)
|
||||
newLink.next = head; // newLink <--> currenthead(head)
|
||||
head = newLink; // newLink(head) <--> oldhead
|
||||
++size;
|
||||
}
|
||||
|
||||
/**
|
||||
* Insert an element at the tail
|
||||
*
|
||||
* @param x Element to be inserted
|
||||
*/
|
||||
public void insertTail(int x) {
|
||||
Link newLink = new Link(x);
|
||||
newLink.next = null; // currentTail(tail) newlink -->
|
||||
if (isEmpty()) { // Check if there are no elements in list then it adds first element
|
||||
tail = newLink;
|
||||
head = tail;
|
||||
} else {
|
||||
tail.next = newLink; // currentTail(tail) --> newLink -->
|
||||
newLink.previous = tail; // currentTail(tail) <--> newLink -->
|
||||
tail = newLink; // oldTail <--> newLink(tail) -->
|
||||
}
|
||||
++size;
|
||||
}
|
||||
|
||||
/**
|
||||
* Insert an element at the head
|
||||
*
|
||||
* @param x Element to be inserted
|
||||
*/
|
||||
public void insertHead(int x) {
|
||||
Link newLink = new Link(x); // Create a new link with a value attached to it
|
||||
if (isEmpty()) // Set the first element added to be the tail
|
||||
tail = newLink;
|
||||
else
|
||||
head.previous = newLink; // newLink <-- currenthead(head)
|
||||
newLink.next = head; // newLink <--> currenthead(head)
|
||||
head = newLink; // newLink(head) <--> oldhead
|
||||
++size;
|
||||
}
|
||||
|
||||
/**
|
||||
* Insert an element at the tail
|
||||
*
|
||||
* @param x Element to be inserted
|
||||
*/
|
||||
public void insertTail(int x) {
|
||||
/**
|
||||
* Insert an element at the index
|
||||
*
|
||||
* @param x Element to be inserted
|
||||
* @param index Index(from start) at which the element x to be inserted
|
||||
*/
|
||||
public void insertElementByIndex(int x, int index) {
|
||||
if (index > size) throw new IndexOutOfBoundsException("Index: " + index + ", Size: " + size);
|
||||
if (index == 0) {
|
||||
insertHead(x);
|
||||
} else {
|
||||
if (index == size) {
|
||||
insertTail(x);
|
||||
} else {
|
||||
Link newLink = new Link(x);
|
||||
newLink.next = null; // currentTail(tail) newlink -->
|
||||
if (isEmpty()) { // Check if there are no elements in list then it adds first element
|
||||
tail = newLink;
|
||||
head = tail;
|
||||
} else {
|
||||
tail.next = newLink; // currentTail(tail) --> newLink -->
|
||||
newLink.previous = tail; // currentTail(tail) <--> newLink -->
|
||||
tail = newLink; // oldTail <--> newLink(tail) -->
|
||||
Link previousLink = head; //
|
||||
for (int i = 1; i < index; i++) { // Loop to reach the index
|
||||
previousLink = previousLink.next;
|
||||
}
|
||||
++size;
|
||||
// previousLink is the Link at index - 1 from start
|
||||
previousLink.next.previous = newLink;
|
||||
newLink.next = previousLink.next;
|
||||
newLink.previous = previousLink;
|
||||
previousLink.next = newLink;
|
||||
}
|
||||
}
|
||||
++size;
|
||||
}
|
||||
|
||||
/**
|
||||
* Delete the element at the head
|
||||
*
|
||||
* @return The new head
|
||||
*/
|
||||
public Link deleteHead() {
|
||||
Link temp = head;
|
||||
head = head.next; // oldHead <--> 2ndElement(head)
|
||||
|
||||
if (head == null) {
|
||||
tail = null;
|
||||
} else {
|
||||
head.previous =
|
||||
null; // oldHead --> 2ndElement(head) nothing pointing at old head so will be removed
|
||||
}
|
||||
--size;
|
||||
return temp;
|
||||
}
|
||||
|
||||
/**
|
||||
* Delete the element at the tail
|
||||
*
|
||||
* @return The new tail
|
||||
*/
|
||||
public Link deleteTail() {
|
||||
Link temp = tail;
|
||||
tail = tail.previous; // 2ndLast(tail) <--> oldTail --> null
|
||||
|
||||
if (tail == null) {
|
||||
head = null;
|
||||
} else {
|
||||
tail.next = null; // 2ndLast(tail) --> null
|
||||
}
|
||||
--size;
|
||||
return temp;
|
||||
}
|
||||
|
||||
/**
|
||||
* Delete the element from somewhere in the list
|
||||
*
|
||||
* @param x element to be deleted
|
||||
* @return Link deleted
|
||||
*/
|
||||
public void delete(int x) {
|
||||
Link current = head;
|
||||
|
||||
while (current.value != x) { // Find the position to delete
|
||||
if (current != tail) {
|
||||
current = current.next;
|
||||
} else { // If we reach the tail and the element is still not found
|
||||
throw new RuntimeException("The element to be deleted does not exist!");
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Insert an element at the index
|
||||
*
|
||||
* @param x Element to be inserted
|
||||
* @param index Index(from start) at which the element x to be inserted
|
||||
*
|
||||
*/
|
||||
public void insertElementByIndex(int x,int index){
|
||||
if(index > size) throw new IndexOutOfBoundsException("Index: " + index + ", Size: " + size);
|
||||
if(index == 0){
|
||||
insertHead(x);
|
||||
}else{
|
||||
if(index == size){
|
||||
insertTail(x);
|
||||
}else{
|
||||
Link newLink = new Link(x);
|
||||
Link previousLink = head; //
|
||||
for(int i = 1; i < index; i++){ //Loop to reach the index
|
||||
previousLink = previousLink.next;
|
||||
}
|
||||
// previousLink is the Link at index - 1 from start
|
||||
previousLink.next.previous = newLink;
|
||||
newLink.next = previousLink.next;
|
||||
newLink.previous = previousLink;
|
||||
previousLink.next = newLink;
|
||||
}
|
||||
}
|
||||
++size;
|
||||
|
||||
if (current == head) deleteHead();
|
||||
else if (current == tail) deleteTail();
|
||||
else { // Before: 1 <--> 2(current) <--> 3
|
||||
current.previous.next = current.next; // 1 --> 3
|
||||
current.next.previous = current.previous; // 1 <--> 3
|
||||
}
|
||||
--size;
|
||||
}
|
||||
|
||||
/**
|
||||
* Delete the element at the head
|
||||
*
|
||||
* @return The new head
|
||||
*/
|
||||
public Link deleteHead() {
|
||||
Link temp = head;
|
||||
head = head.next; // oldHead <--> 2ndElement(head)
|
||||
/**
|
||||
* Inserts element and reorders
|
||||
*
|
||||
* @param x Element to be added
|
||||
*/
|
||||
public void insertOrdered(int x) {
|
||||
Link newLink = new Link(x);
|
||||
Link current = head;
|
||||
while (current != null && x > current.value) // Find the position to insert
|
||||
current = current.next;
|
||||
|
||||
if (head == null) {
|
||||
tail = null;
|
||||
} else {
|
||||
head.previous = null; // oldHead --> 2ndElement(head) nothing pointing at old head so will be removed
|
||||
}
|
||||
--size;
|
||||
return temp;
|
||||
if (current == head) insertHead(x);
|
||||
else if (current == null) insertTail(x);
|
||||
else { // Before: 1 <--> 2(current) <--> 3
|
||||
newLink.previous = current.previous; // 1 <-- newLink
|
||||
current.previous.next = newLink; // 1 <--> newLink
|
||||
newLink.next = current; // 1 <--> newLink --> 2(current) <--> 3
|
||||
current.previous = newLink; // 1 <--> newLink <--> 2(current) <--> 3
|
||||
}
|
||||
++size;
|
||||
}
|
||||
|
||||
/**
|
||||
* Delete the element at the tail
|
||||
*
|
||||
* @return The new tail
|
||||
*/
|
||||
public Link deleteTail() {
|
||||
Link temp = tail;
|
||||
tail = tail.previous; // 2ndLast(tail) <--> oldTail --> null
|
||||
|
||||
if (tail == null) {
|
||||
head = null;
|
||||
} else{
|
||||
tail.next = null; // 2ndLast(tail) --> null
|
||||
}
|
||||
--size;
|
||||
return temp;
|
||||
/**
|
||||
* Deletes the passed node from the current list
|
||||
*
|
||||
* @param z Element to be deleted
|
||||
*/
|
||||
public void deleteNode(Link z) {
|
||||
if (z.next == null) {
|
||||
deleteTail();
|
||||
} else if (z == head) {
|
||||
deleteHead();
|
||||
} else { // before <-- 1 <--> 2(z) <--> 3 -->
|
||||
z.previous.next = z.next; // 1 --> 3
|
||||
z.next.previous = z.previous; // 1 <--> 3
|
||||
}
|
||||
--size;
|
||||
}
|
||||
|
||||
/**
|
||||
* Delete the element from somewhere in the list
|
||||
*
|
||||
* @param x element to be deleted
|
||||
* @return Link deleted
|
||||
*/
|
||||
public void delete(int x) {
|
||||
Link current = head;
|
||||
|
||||
while (current.value != x) {// Find the position to delete
|
||||
if (current != tail) {
|
||||
current = current.next;
|
||||
} else {// If we reach the tail and the element is still not found
|
||||
throw new RuntimeException("The element to be deleted does not exist!");
|
||||
}
|
||||
}
|
||||
|
||||
if (current == head)
|
||||
deleteHead();
|
||||
|
||||
else if (current == tail)
|
||||
deleteTail();
|
||||
|
||||
else { // Before: 1 <--> 2(current) <--> 3
|
||||
current.previous.next = current.next; // 1 --> 3
|
||||
current.next.previous = current.previous; // 1 <--> 3
|
||||
}
|
||||
--size;
|
||||
public static void removeDuplicates(DoublyLinkedList l) {
|
||||
Link linkOne = l.head;
|
||||
while (linkOne.next != null) { // list is present
|
||||
Link linkTwo = linkOne.next; // second link for comparison
|
||||
while (linkTwo.next != null) {
|
||||
if (linkOne.value == linkTwo.value) // if there are duplicates values then
|
||||
l.delete(linkTwo.value); // delete the link
|
||||
linkTwo = linkTwo.next; // go to next link
|
||||
}
|
||||
linkOne = linkOne.next; // go to link link to iterate the whole list again
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Inserts element and reorders
|
||||
*
|
||||
* @param x Element to be added
|
||||
*/
|
||||
public void insertOrdered(int x) {
|
||||
Link newLink = new Link(x);
|
||||
Link current = head;
|
||||
while (current != null && x > current.value) // Find the position to insert
|
||||
current = current.next;
|
||||
/** Clears List */
|
||||
public void clearList() {
|
||||
head = null;
|
||||
tail = null;
|
||||
size = 0;
|
||||
}
|
||||
|
||||
if (current == head)
|
||||
insertHead(x);
|
||||
/**
|
||||
* Returns true if list is empty
|
||||
*
|
||||
* @return true if list is empty
|
||||
*/
|
||||
public boolean isEmpty() {
|
||||
return (head == null);
|
||||
}
|
||||
|
||||
else if (current == null)
|
||||
insertTail(x);
|
||||
|
||||
else { // Before: 1 <--> 2(current) <--> 3
|
||||
newLink.previous = current.previous; // 1 <-- newLink
|
||||
current.previous.next = newLink; // 1 <--> newLink
|
||||
newLink.next = current; // 1 <--> newLink --> 2(current) <--> 3
|
||||
current.previous = newLink; // 1 <--> newLink <--> 2(current) <--> 3
|
||||
}
|
||||
++size;
|
||||
}
|
||||
|
||||
/**
|
||||
* Deletes the passed node from the current list
|
||||
*
|
||||
* @param z Element to be deleted
|
||||
*/
|
||||
public void deleteNode(Link z) {
|
||||
if(z.next == null){
|
||||
deleteTail();
|
||||
} else if(z == head){
|
||||
deleteHead();
|
||||
} else{ //before <-- 1 <--> 2(z) <--> 3 -->
|
||||
z.previous.next = z.next; // 1 --> 3
|
||||
z.next.previous = z.previous; // 1 <--> 3
|
||||
}
|
||||
--size;
|
||||
}
|
||||
|
||||
public static void removeDuplicates(DoublyLinkedList l ) {
|
||||
Link linkOne = l.head ;
|
||||
while(linkOne.next != null) { // list is present
|
||||
Link linkTwo = linkOne.next; // second link for comparison
|
||||
while(linkTwo.next!= null) {
|
||||
if(linkOne.value == linkTwo.value) // if there are duplicates values then
|
||||
l.delete(linkTwo.value); // delete the link
|
||||
linkTwo = linkTwo.next ; // go to next link
|
||||
}
|
||||
linkOne = linkOne.next; // go to link link to iterate the whole list again
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Clears List
|
||||
*
|
||||
*/
|
||||
public void clearList(){
|
||||
head = null;
|
||||
tail = null;
|
||||
size = 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns true if list is empty
|
||||
*
|
||||
* @return true if list is empty
|
||||
*/
|
||||
public boolean isEmpty() {
|
||||
return (head == null);
|
||||
}
|
||||
|
||||
/**
|
||||
* Prints contents of the list
|
||||
*/
|
||||
public void display() { // Prints contents of the list
|
||||
Link current = head;
|
||||
while (current != null) {
|
||||
current.displayLink();
|
||||
current = current.next;
|
||||
}
|
||||
System.out.println();
|
||||
/** Prints contents of the list */
|
||||
public void display() { // Prints contents of the list
|
||||
Link current = head;
|
||||
while (current != null) {
|
||||
current.displayLink();
|
||||
current = current.next;
|
||||
}
|
||||
System.out.println();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* This class is used to implement the nodes of the
|
||||
* linked list.
|
||||
* This class is used to implement the nodes of the linked list.
|
||||
*
|
||||
* @author Unknown
|
||||
*/
|
||||
class Link {
|
||||
/**
|
||||
* Value of node
|
||||
*/
|
||||
public int value;
|
||||
/**
|
||||
* This points to the link in front of the new link
|
||||
*/
|
||||
public Link next;
|
||||
/**
|
||||
* This points to the link behind the new link
|
||||
*/
|
||||
public Link previous;
|
||||
/** Value of node */
|
||||
public int value;
|
||||
/** This points to the link in front of the new link */
|
||||
public Link next;
|
||||
/** This points to the link behind the new link */
|
||||
public Link previous;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*
|
||||
* @param value Value of node
|
||||
*/
|
||||
public Link(int value) {
|
||||
this.value = value;
|
||||
}
|
||||
/**
|
||||
* Constructor
|
||||
*
|
||||
* @param value Value of node
|
||||
*/
|
||||
public Link(int value) {
|
||||
this.value = value;
|
||||
}
|
||||
|
||||
/**
|
||||
* Displays the node
|
||||
*/
|
||||
public void displayLink() {
|
||||
System.out.print(value + " ");
|
||||
}
|
||||
/** Displays the node */
|
||||
public void displayLink() {
|
||||
System.out.print(value + " ");
|
||||
}
|
||||
|
||||
/**
|
||||
* Main Method
|
||||
*
|
||||
* @param args Command line arguments
|
||||
*/
|
||||
public static void main(String args[]) {
|
||||
DoublyLinkedList myList = new DoublyLinkedList();
|
||||
myList.insertHead(13);
|
||||
myList.insertHead(7);
|
||||
myList.insertHead(10);
|
||||
myList.display(); // <-- 10(head) <--> 7 <--> 13(tail) -->
|
||||
/**
|
||||
* Main Method
|
||||
*
|
||||
* @param args Command line arguments
|
||||
*/
|
||||
public static void main(String args[]) {
|
||||
DoublyLinkedList myList = new DoublyLinkedList();
|
||||
myList.insertHead(13);
|
||||
myList.insertHead(7);
|
||||
myList.insertHead(10);
|
||||
myList.display(); // <-- 10(head) <--> 7 <--> 13(tail) -->
|
||||
|
||||
myList.insertTail(11);
|
||||
myList.display(); // <-- 10(head) <--> 7 <--> 13 <--> 11(tail) -->
|
||||
myList.insertTail(11);
|
||||
myList.display(); // <-- 10(head) <--> 7 <--> 13 <--> 11(tail) -->
|
||||
|
||||
myList.deleteTail();
|
||||
myList.display(); // <-- 10(head) <--> 7 <--> 13(tail) -->
|
||||
myList.deleteTail();
|
||||
myList.display(); // <-- 10(head) <--> 7 <--> 13(tail) -->
|
||||
|
||||
myList.delete(7);
|
||||
myList.display(); // <-- 10(head) <--> 13(tail) -->
|
||||
myList.delete(7);
|
||||
myList.display(); // <-- 10(head) <--> 13(tail) -->
|
||||
|
||||
myList.insertOrdered(23);
|
||||
myList.insertOrdered(67);
|
||||
myList.insertOrdered(3);
|
||||
myList.display(); // <-- 3(head) <--> 10 <--> 13 <--> 23 <--> 67(tail) -->
|
||||
myList.insertElementByIndex(5, 1);
|
||||
myList.display(); // <-- 3(head) <--> 5 <--> 10 <--> 13 <--> 23 <--> 67(tail) -->
|
||||
myList.clearList();
|
||||
myList.display();
|
||||
myList.insertHead(20);
|
||||
myList.display();
|
||||
}
|
||||
myList.insertOrdered(23);
|
||||
myList.insertOrdered(67);
|
||||
myList.insertOrdered(3);
|
||||
myList.display(); // <-- 3(head) <--> 10 <--> 13 <--> 23 <--> 67(tail) -->
|
||||
myList.insertElementByIndex(5, 1);
|
||||
myList.display(); // <-- 3(head) <--> 5 <--> 10 <--> 13 <--> 23 <--> 67(tail) -->
|
||||
myList.clearList();
|
||||
myList.display();
|
||||
myList.insertHead(20);
|
||||
myList.display();
|
||||
}
|
||||
}
|
||||
|
@ -3,58 +3,54 @@ package DataStructures.Lists;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* @author https://github.com/shellhub
|
||||
*/
|
||||
|
||||
/** @author https://github.com/shellhub */
|
||||
public class MergeSortedArrayList {
|
||||
public static void main(String[] args) {
|
||||
List<Integer> listA = new ArrayList<>();
|
||||
List<Integer> listB = new ArrayList<>();
|
||||
List<Integer> listC = new ArrayList<>();
|
||||
public static void main(String[] args) {
|
||||
List<Integer> listA = new ArrayList<>();
|
||||
List<Integer> listB = new ArrayList<>();
|
||||
List<Integer> listC = new ArrayList<>();
|
||||
|
||||
/* init ListA and List B */
|
||||
for (int i = 1; i <= 10; i += 2) {
|
||||
listA.add(i); /* listA: [1, 3, 5, 7, 9] */
|
||||
listB.add(i + 1); /* listB: [2, 4, 6, 8, 10] */
|
||||
}
|
||||
|
||||
/* merge listA and listB to listC */
|
||||
merge(listA, listB, listC);
|
||||
|
||||
System.out.println("listA: " + listA);
|
||||
System.out.println("listB: " + listB);
|
||||
System.out.println("listC: " + listC);
|
||||
/* init ListA and List B */
|
||||
for (int i = 1; i <= 10; i += 2) {
|
||||
listA.add(i); /* listA: [1, 3, 5, 7, 9] */
|
||||
listB.add(i + 1); /* listB: [2, 4, 6, 8, 10] */
|
||||
}
|
||||
|
||||
/**
|
||||
* merge two sorted ArrayList
|
||||
*
|
||||
* @param listA the first list to merge
|
||||
* @param listB the second list to merge
|
||||
* @param listC the result list after merging
|
||||
*/
|
||||
public static void merge(List<Integer> listA, List<Integer> listB, List<Integer> listC) {
|
||||
int pa = 0; /* the index of listA */
|
||||
int pb = 0; /* the index of listB */
|
||||
/* merge listA and listB to listC */
|
||||
merge(listA, listB, listC);
|
||||
|
||||
while (pa < listA.size() && pb < listB.size()) {
|
||||
if (listA.get(pa) <= listB.get(pb)) {
|
||||
listC.add(listA.get(pa++));
|
||||
} else {
|
||||
listC.add(listB.get(pb++));
|
||||
}
|
||||
}
|
||||
System.out.println("listA: " + listA);
|
||||
System.out.println("listB: " + listB);
|
||||
System.out.println("listC: " + listC);
|
||||
}
|
||||
|
||||
/* copy left element of listA to listC */
|
||||
while (pa < listA.size()) {
|
||||
listC.add(listA.get(pa++));
|
||||
}
|
||||
/**
|
||||
* merge two sorted ArrayList
|
||||
*
|
||||
* @param listA the first list to merge
|
||||
* @param listB the second list to merge
|
||||
* @param listC the result list after merging
|
||||
*/
|
||||
public static void merge(List<Integer> listA, List<Integer> listB, List<Integer> listC) {
|
||||
int pa = 0; /* the index of listA */
|
||||
int pb = 0; /* the index of listB */
|
||||
|
||||
/* copy left element of listB to listC */
|
||||
while (pb < listB.size()) {
|
||||
listC.add(listB.get(pb++));
|
||||
}
|
||||
while (pa < listA.size() && pb < listB.size()) {
|
||||
if (listA.get(pa) <= listB.get(pb)) {
|
||||
listC.add(listA.get(pa++));
|
||||
} else {
|
||||
listC.add(listB.get(pb++));
|
||||
}
|
||||
}
|
||||
|
||||
/* copy left element of listA to listC */
|
||||
while (pa < listA.size()) {
|
||||
listC.add(listA.get(pa++));
|
||||
}
|
||||
|
||||
/* copy left element of listB to listC */
|
||||
while (pb < listB.size()) {
|
||||
listC.add(listB.get(pb++));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -2,50 +2,50 @@ package DataStructures.Lists;
|
||||
|
||||
public class MergeSortedSinglyLinkedList extends SinglyLinkedList {
|
||||
|
||||
public static void main(String[] args) {
|
||||
SinglyLinkedList listA = new SinglyLinkedList();
|
||||
SinglyLinkedList listB = new SinglyLinkedList();
|
||||
public static void main(String[] args) {
|
||||
SinglyLinkedList listA = new SinglyLinkedList();
|
||||
SinglyLinkedList listB = new SinglyLinkedList();
|
||||
|
||||
for (int i = 2; i <= 10; i += 2) {
|
||||
listA.insert(i);
|
||||
listB.insert(i - 1);
|
||||
}
|
||||
assert listA.toString().equals("2->4->6->8->10");
|
||||
assert listB.toString().equals("1->3->5->7->9");
|
||||
assert merge(listA, listB).toString().equals("1->2->3->4->5->6->7->8->9->10");
|
||||
for (int i = 2; i <= 10; i += 2) {
|
||||
listA.insert(i);
|
||||
listB.insert(i - 1);
|
||||
}
|
||||
assert listA.toString().equals("2->4->6->8->10");
|
||||
assert listB.toString().equals("1->3->5->7->9");
|
||||
assert merge(listA, listB).toString().equals("1->2->3->4->5->6->7->8->9->10");
|
||||
}
|
||||
|
||||
/**
|
||||
* Merge two sorted SingleLinkedList
|
||||
*
|
||||
* @param listA the first sorted list
|
||||
* @param listB the second sored list
|
||||
* @return merged sorted list
|
||||
*/
|
||||
public static SinglyLinkedList merge(SinglyLinkedList listA, SinglyLinkedList listB) {
|
||||
Node headA = listA.getHead();
|
||||
Node headB = listB.getHead();
|
||||
/**
|
||||
* Merge two sorted SingleLinkedList
|
||||
*
|
||||
* @param listA the first sorted list
|
||||
* @param listB the second sored list
|
||||
* @return merged sorted list
|
||||
*/
|
||||
public static SinglyLinkedList merge(SinglyLinkedList listA, SinglyLinkedList listB) {
|
||||
Node headA = listA.getHead();
|
||||
Node headB = listB.getHead();
|
||||
|
||||
int size = listA.size() + listB.size();
|
||||
int size = listA.size() + listB.size();
|
||||
|
||||
Node head = new Node();
|
||||
Node tail = head;
|
||||
while (headA != null && headB != null) {
|
||||
if (headA.value <= headB.value) {
|
||||
tail.next = headA;
|
||||
headA = headA.next;
|
||||
} else {
|
||||
tail.next = headB;
|
||||
headB = headB.next;
|
||||
}
|
||||
tail = tail.next;
|
||||
}
|
||||
if (headA == null) {
|
||||
tail.next = headB;
|
||||
}
|
||||
if (headB == null) {
|
||||
tail.next = headA;
|
||||
}
|
||||
return new SinglyLinkedList(head.next, size);
|
||||
Node head = new Node();
|
||||
Node tail = head;
|
||||
while (headA != null && headB != null) {
|
||||
if (headA.value <= headB.value) {
|
||||
tail.next = headA;
|
||||
headA = headA.next;
|
||||
} else {
|
||||
tail.next = headB;
|
||||
headB = headB.next;
|
||||
}
|
||||
tail = tail.next;
|
||||
}
|
||||
if (headA == null) {
|
||||
tail.next = headB;
|
||||
}
|
||||
if (headB == null) {
|
||||
tail.next = headA;
|
||||
}
|
||||
return new SinglyLinkedList(head.next, size);
|
||||
}
|
||||
}
|
||||
|
@ -4,53 +4,51 @@ import java.util.Arrays;
|
||||
import java.util.Comparator;
|
||||
import java.util.PriorityQueue;
|
||||
|
||||
/**
|
||||
* @author Arun Pandey (https://github.com/pandeyarun709)
|
||||
*/
|
||||
/** @author Arun Pandey (https://github.com/pandeyarun709) */
|
||||
public class Merge_K_SortedLinkedlist {
|
||||
|
||||
/**
|
||||
* This function merge K sorted LinkedList
|
||||
*
|
||||
* @param a array of LinkedList
|
||||
* @param N size of array
|
||||
* @return node
|
||||
*/
|
||||
Node mergeKList(Node[] a, int N) {
|
||||
// Min Heap
|
||||
PriorityQueue<Node> min = new PriorityQueue<>(Comparator.comparingInt(x -> x.data));
|
||||
/**
|
||||
* This function merge K sorted LinkedList
|
||||
*
|
||||
* @param a array of LinkedList
|
||||
* @param N size of array
|
||||
* @return node
|
||||
*/
|
||||
Node mergeKList(Node[] a, int N) {
|
||||
// Min Heap
|
||||
PriorityQueue<Node> min = new PriorityQueue<>(Comparator.comparingInt(x -> x.data));
|
||||
|
||||
// adding head of all linkedList in min heap
|
||||
min.addAll(Arrays.asList(a).subList(0, N));
|
||||
// adding head of all linkedList in min heap
|
||||
min.addAll(Arrays.asList(a).subList(0, N));
|
||||
|
||||
// Make new head among smallest heads in K linkedList
|
||||
Node head = min.poll();
|
||||
min.add(head.next);
|
||||
Node curr = head;
|
||||
// Make new head among smallest heads in K linkedList
|
||||
Node head = min.poll();
|
||||
min.add(head.next);
|
||||
Node curr = head;
|
||||
|
||||
// merging LinkedList
|
||||
while (!min.isEmpty()) {
|
||||
// merging LinkedList
|
||||
while (!min.isEmpty()) {
|
||||
|
||||
Node temp = min.poll();
|
||||
curr.next = temp;
|
||||
curr = temp;
|
||||
Node temp = min.poll();
|
||||
curr.next = temp;
|
||||
curr = temp;
|
||||
|
||||
// Add Node in min Heap only if temp.next is not null
|
||||
if (temp.next != null) {
|
||||
min.add(temp.next);
|
||||
}
|
||||
}
|
||||
|
||||
return head;
|
||||
// Add Node in min Heap only if temp.next is not null
|
||||
if (temp.next != null) {
|
||||
min.add(temp.next);
|
||||
}
|
||||
}
|
||||
|
||||
private class Node {
|
||||
private int data;
|
||||
private Node next;
|
||||
return head;
|
||||
}
|
||||
|
||||
public Node(int d) {
|
||||
this.data = d;
|
||||
next = null;
|
||||
}
|
||||
private class Node {
|
||||
private int data;
|
||||
private Node next;
|
||||
|
||||
public Node(int d) {
|
||||
this.data = d;
|
||||
next = null;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1,32 +1,31 @@
|
||||
package DataStructures.Lists;
|
||||
|
||||
public class SearchSinglyLinkedListRecursion extends SinglyLinkedList {
|
||||
public static void main(String[] args) {
|
||||
SearchSinglyLinkedListRecursion list = new SearchSinglyLinkedListRecursion();
|
||||
for (int i = 1; i <= 10; ++i) {
|
||||
list.insert(i);
|
||||
}
|
||||
|
||||
for (int i = 1; i <= 10; ++i) {
|
||||
assert list.search(i);
|
||||
}
|
||||
assert !list.search(-1)
|
||||
&& !list.search(100);
|
||||
public static void main(String[] args) {
|
||||
SearchSinglyLinkedListRecursion list = new SearchSinglyLinkedListRecursion();
|
||||
for (int i = 1; i <= 10; ++i) {
|
||||
list.insert(i);
|
||||
}
|
||||
|
||||
/**
|
||||
* Test if the value key is present in the list using recursion.
|
||||
*
|
||||
* @param node the head node.
|
||||
* @param key the value to be searched.
|
||||
* @return {@code true} if key is present in the list, otherwise {@code false}.
|
||||
*/
|
||||
private boolean searchRecursion(Node node, int key) {
|
||||
return node != null && (node.value == key || searchRecursion(node.next, key));
|
||||
for (int i = 1; i <= 10; ++i) {
|
||||
assert list.search(i);
|
||||
}
|
||||
assert !list.search(-1) && !list.search(100);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean search(int key) {
|
||||
return searchRecursion(getHead(), key);
|
||||
}
|
||||
/**
|
||||
* Test if the value key is present in the list using recursion.
|
||||
*
|
||||
* @param node the head node.
|
||||
* @param key the value to be searched.
|
||||
* @return {@code true} if key is present in the list, otherwise {@code false}.
|
||||
*/
|
||||
private boolean searchRecursion(Node node, int key) {
|
||||
return node != null && (node.value == key || searchRecursion(node.next, key));
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean search(int key) {
|
||||
return searchRecursion(getHead(), key);
|
||||
}
|
||||
}
|
||||
|
@ -1,333 +1,301 @@
|
||||
package DataStructures.Lists;
|
||||
|
||||
/**
|
||||
* This class implements a SinglyLinked List. This is done
|
||||
* using SinglyLinkedList class and a LinkForLinkedList Class.
|
||||
* <p>
|
||||
* A linked list is similar to an array, it hold values.
|
||||
* However, links in a linked list do not have indexes. With
|
||||
* a linked list you do not need to predetermine it's size as
|
||||
* it grows and shrinks as it is edited. This is an example of
|
||||
* a singly linked list. Elements can only be added/removed
|
||||
* at the head/front of the list.
|
||||
* This class implements a SinglyLinked List. This is done using SinglyLinkedList class and a
|
||||
* LinkForLinkedList Class.
|
||||
*
|
||||
* <p>A linked list is similar to an array, it hold values. However, links in a linked list do not
|
||||
* have indexes. With a linked list you do not need to predetermine it's size as it grows and
|
||||
* shrinks as it is edited. This is an example of a singly linked list. Elements can only be
|
||||
* added/removed at the head/front of the list.
|
||||
*/
|
||||
public class SinglyLinkedList {
|
||||
/**
|
||||
* Head refer to the front of the list
|
||||
*/
|
||||
private Node head;
|
||||
/** Head refer to the front of the list */
|
||||
private Node head;
|
||||
|
||||
/**
|
||||
* Size of SinglyLinkedList
|
||||
*/
|
||||
private int size;
|
||||
/** Size of SinglyLinkedList */
|
||||
private int size;
|
||||
|
||||
/**
|
||||
* Init SinglyLinkedList
|
||||
*/
|
||||
public SinglyLinkedList() {
|
||||
head = null;
|
||||
size = 0;
|
||||
/** Init SinglyLinkedList */
|
||||
public SinglyLinkedList() {
|
||||
head = null;
|
||||
size = 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Init SinglyLinkedList with specified head node and size
|
||||
*
|
||||
* @param head the head node of list
|
||||
* @param size the size of list
|
||||
*/
|
||||
public SinglyLinkedList(Node head, int size) {
|
||||
this.head = head;
|
||||
this.size = size;
|
||||
}
|
||||
|
||||
/**
|
||||
* Inserts an element at the head of the list
|
||||
*
|
||||
* @param x element to be added
|
||||
*/
|
||||
public void insertHead(int x) {
|
||||
insertNth(x, 0);
|
||||
}
|
||||
|
||||
/**
|
||||
* Insert an element at the tail of the list
|
||||
*
|
||||
* @param data element to be added
|
||||
*/
|
||||
public void insert(int data) {
|
||||
insertNth(data, size);
|
||||
}
|
||||
|
||||
/**
|
||||
* Inserts a new node at a specified position of the list
|
||||
*
|
||||
* @param data data to be stored in a new node
|
||||
* @param position position at which a new node is to be inserted
|
||||
*/
|
||||
public void insertNth(int data, int position) {
|
||||
checkBounds(position, 0, size);
|
||||
Node newNode = new Node(data);
|
||||
if (head == null) {
|
||||
/* the list is empty */
|
||||
head = newNode;
|
||||
size++;
|
||||
return;
|
||||
} else if (position == 0) {
|
||||
/* insert at the head of the list */
|
||||
newNode.next = head;
|
||||
head = newNode;
|
||||
size++;
|
||||
return;
|
||||
}
|
||||
Node cur = head;
|
||||
for (int i = 0; i < position - 1; ++i) {
|
||||
cur = cur.next;
|
||||
}
|
||||
newNode.next = cur.next;
|
||||
cur.next = newNode;
|
||||
size++;
|
||||
}
|
||||
|
||||
/** Deletes a node at the head */
|
||||
public void deleteHead() {
|
||||
deleteNth(0);
|
||||
}
|
||||
|
||||
/** Deletes an element at the tail */
|
||||
public void delete() {
|
||||
deleteNth(size - 1);
|
||||
}
|
||||
|
||||
/** Deletes an element at Nth position */
|
||||
public void deleteNth(int position) {
|
||||
checkBounds(position, 0, size - 1);
|
||||
if (position == 0) {
|
||||
Node destroy = head;
|
||||
head = head.next;
|
||||
destroy = null; /* clear to let GC do its work */
|
||||
size--;
|
||||
return;
|
||||
}
|
||||
Node cur = head;
|
||||
for (int i = 0; i < position - 1; ++i) {
|
||||
cur = cur.next;
|
||||
}
|
||||
|
||||
/**
|
||||
* Init SinglyLinkedList with specified head node and size
|
||||
*
|
||||
* @param head the head node of list
|
||||
* @param size the size of list
|
||||
*/
|
||||
public SinglyLinkedList(Node head, int size) {
|
||||
this.head = head;
|
||||
this.size = size;
|
||||
Node destroy = cur.next;
|
||||
cur.next = cur.next.next;
|
||||
destroy = null; // clear to let GC do its work
|
||||
|
||||
size--;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param position to check position
|
||||
* @param low low index
|
||||
* @param high high index
|
||||
* @throws IndexOutOfBoundsException if {@code position} not in range {@code low} to {@code high}
|
||||
*/
|
||||
public void checkBounds(int position, int low, int high) {
|
||||
if (position > high || position < low) {
|
||||
throw new IndexOutOfBoundsException(position + "");
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Inserts an element at the head of the list
|
||||
*
|
||||
* @param x element to be added
|
||||
*/
|
||||
public void insertHead(int x) {
|
||||
insertNth(x, 0);
|
||||
/** Clear all nodes in the list */
|
||||
public void clear() {
|
||||
Node cur = head;
|
||||
while (cur != null) {
|
||||
Node prev = cur;
|
||||
cur = cur.next;
|
||||
prev = null; // clear to let GC do its work
|
||||
}
|
||||
head = null;
|
||||
size = 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Insert an element at the tail of the list
|
||||
*
|
||||
* @param data element to be added
|
||||
*/
|
||||
public void insert(int data) {
|
||||
insertNth(data, size);
|
||||
/**
|
||||
* Checks if the list is empty
|
||||
*
|
||||
* @return {@code true} if list is empty, otherwise {@code false}.
|
||||
*/
|
||||
public boolean isEmpty() {
|
||||
return size == 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the size of the linked list.
|
||||
*
|
||||
* @return the size of the list.
|
||||
*/
|
||||
public int size() {
|
||||
return size;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get head of the list.
|
||||
*
|
||||
* @return head of the list.
|
||||
*/
|
||||
public Node getHead() {
|
||||
return head;
|
||||
}
|
||||
|
||||
/**
|
||||
* Calculate the count of the list manually
|
||||
*
|
||||
* @return count of the list
|
||||
*/
|
||||
public int count() {
|
||||
int count = 0;
|
||||
Node cur = head;
|
||||
while (cur != null) {
|
||||
cur = cur.next;
|
||||
count++;
|
||||
}
|
||||
return count;
|
||||
}
|
||||
|
||||
/**
|
||||
* Inserts a new node at a specified position of the list
|
||||
*
|
||||
* @param data data to be stored in a new node
|
||||
* @param position position at which a new node is to be inserted
|
||||
*/
|
||||
public void insertNth(int data, int position) {
|
||||
checkBounds(position, 0, size);
|
||||
Node newNode = new Node(data);
|
||||
if (head == null) { /* the list is empty */
|
||||
head = newNode;
|
||||
size++;
|
||||
return;
|
||||
} else if (position == 0) { /* insert at the head of the list */
|
||||
newNode.next = head;
|
||||
head = newNode;
|
||||
size++;
|
||||
return;
|
||||
}
|
||||
Node cur = head;
|
||||
for (int i = 0; i < position - 1; ++i) {
|
||||
cur = cur.next;
|
||||
}
|
||||
newNode.next = cur.next;
|
||||
cur.next = newNode;
|
||||
size++;
|
||||
/**
|
||||
* Test if the value key is present in the list.
|
||||
*
|
||||
* @param key the value to be searched.
|
||||
* @return {@code true} if key is present in the list, otherwise {@code false}.
|
||||
*/
|
||||
public boolean search(int key) {
|
||||
Node cur = head;
|
||||
while (cur != null) {
|
||||
if (cur.value == key) {
|
||||
return true;
|
||||
}
|
||||
cur = cur.next;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Deletes a node at the head
|
||||
*/
|
||||
public void deleteHead() {
|
||||
deleteNth(0);
|
||||
/**
|
||||
* Return element at special index.
|
||||
*
|
||||
* @param index given index of element
|
||||
* @return element at special index.
|
||||
*/
|
||||
public int getNth(int index) {
|
||||
checkBounds(index, 0, size - 1);
|
||||
Node cur = head;
|
||||
for (int i = 0; i < index; ++i) {
|
||||
cur = cur.next;
|
||||
}
|
||||
return cur.value;
|
||||
}
|
||||
|
||||
/**
|
||||
* Deletes an element at the tail
|
||||
*/
|
||||
public void delete() {
|
||||
deleteNth(size - 1);
|
||||
@Override
|
||||
public String toString() {
|
||||
if (size == 0) {
|
||||
return "";
|
||||
}
|
||||
|
||||
/**
|
||||
* Deletes an element at Nth position
|
||||
*/
|
||||
public void deleteNth(int position) {
|
||||
checkBounds(position, 0, size - 1);
|
||||
if (position == 0) {
|
||||
Node destroy = head;
|
||||
head = head.next;
|
||||
destroy = null; /* clear to let GC do its work */
|
||||
size--;
|
||||
return;
|
||||
}
|
||||
Node cur = head;
|
||||
for (int i = 0; i < position - 1; ++i) {
|
||||
cur = cur.next;
|
||||
}
|
||||
|
||||
Node destroy = cur.next;
|
||||
cur.next = cur.next.next;
|
||||
destroy = null; // clear to let GC do its work
|
||||
|
||||
size--;
|
||||
StringBuilder builder = new StringBuilder();
|
||||
Node cur = head;
|
||||
while (cur != null) {
|
||||
builder.append(cur.value).append("->");
|
||||
cur = cur.next;
|
||||
}
|
||||
return builder.replace(builder.length() - 2, builder.length(), "").toString();
|
||||
}
|
||||
|
||||
/**
|
||||
* @param position to check position
|
||||
* @param low low index
|
||||
* @param high high index
|
||||
* @throws IndexOutOfBoundsException if {@code position} not in range {@code low} to {@code high}
|
||||
*/
|
||||
public void checkBounds(int position, int low, int high) {
|
||||
if (position > high || position < low) {
|
||||
throw new IndexOutOfBoundsException(position + "");
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Clear all nodes in the list
|
||||
*/
|
||||
public void clear() {
|
||||
Node cur = head;
|
||||
while (cur != null) {
|
||||
Node prev = cur;
|
||||
cur = cur.next;
|
||||
prev = null; // clear to let GC do its work
|
||||
}
|
||||
head = null;
|
||||
size = 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks if the list is empty
|
||||
*
|
||||
* @return {@code true} if list is empty, otherwise {@code false}.
|
||||
*/
|
||||
public boolean isEmpty() {
|
||||
return size == 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the size of the linked list.
|
||||
*
|
||||
* @return the size of the list.
|
||||
*/
|
||||
public int size() {
|
||||
return size;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get head of the list.
|
||||
*
|
||||
* @return head of the list.
|
||||
*/
|
||||
public Node getHead() {
|
||||
return head;
|
||||
}
|
||||
|
||||
/**
|
||||
* Calculate the count of the list manually
|
||||
*
|
||||
* @return count of the list
|
||||
*/
|
||||
public int count() {
|
||||
int count = 0;
|
||||
Node cur = head;
|
||||
while (cur != null) {
|
||||
cur = cur.next;
|
||||
count++;
|
||||
}
|
||||
return count;
|
||||
}
|
||||
|
||||
/**
|
||||
* Test if the value key is present in the list.
|
||||
*
|
||||
* @param key the value to be searched.
|
||||
* @return {@code true} if key is present in the list, otherwise {@code false}.
|
||||
*/
|
||||
public boolean search(int key) {
|
||||
Node cur = head;
|
||||
while (cur != null) {
|
||||
if (cur.value == key) {
|
||||
return true;
|
||||
}
|
||||
cur = cur.next;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return element at special index.
|
||||
*
|
||||
* @param index given index of element
|
||||
* @return element at special index.
|
||||
*/
|
||||
public int getNth(int index) {
|
||||
checkBounds(index, 0, size - 1);
|
||||
Node cur = head;
|
||||
for (int i = 0; i < index; ++i) {
|
||||
cur = cur.next;
|
||||
}
|
||||
return cur.value;
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
if (size == 0) {
|
||||
return "";
|
||||
}
|
||||
StringBuilder builder = new StringBuilder();
|
||||
Node cur = head;
|
||||
while (cur != null) {
|
||||
builder.append(cur.value).append("->");
|
||||
cur = cur.next;
|
||||
}
|
||||
return builder.replace(builder.length() - 2, builder.length(), "").toString();
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Driver Code
|
||||
*/
|
||||
public static void main(String[] arg) {
|
||||
SinglyLinkedList list = new SinglyLinkedList();
|
||||
assert list.isEmpty();
|
||||
assert list.size() == 0
|
||||
&& list.count() == 0;
|
||||
assert list.toString().equals("");
|
||||
|
||||
/* Test insert function */
|
||||
list.insertHead(5);
|
||||
list.insertHead(7);
|
||||
list.insertHead(10);
|
||||
list.insert(3);
|
||||
list.insertNth(1, 4);
|
||||
assert list.toString().equals("10->7->5->3->1");
|
||||
|
||||
/* Test search function */
|
||||
assert list.search(10)
|
||||
&& list.search(5)
|
||||
&& list.search(1)
|
||||
&& !list.search(100);
|
||||
|
||||
/* Test get function */
|
||||
assert list.getNth(0) == 10
|
||||
&& list.getNth(2) == 5
|
||||
&& list.getNth(4) == 1;
|
||||
|
||||
/* Test delete function */
|
||||
list.deleteHead();
|
||||
list.deleteNth(1);
|
||||
list.delete();
|
||||
assert list.toString().equals("7->3");
|
||||
|
||||
assert list.size == 2
|
||||
&& list.size() == list.count();
|
||||
|
||||
list.clear();
|
||||
assert list.isEmpty();
|
||||
|
||||
try {
|
||||
list.delete();
|
||||
assert false; /* this should not happen */
|
||||
} catch (Exception e) {
|
||||
assert true; /* this should happen */
|
||||
}
|
||||
/** Driver Code */
|
||||
public static void main(String[] arg) {
|
||||
SinglyLinkedList list = new SinglyLinkedList();
|
||||
assert list.isEmpty();
|
||||
assert list.size() == 0 && list.count() == 0;
|
||||
assert list.toString().equals("");
|
||||
|
||||
/* Test insert function */
|
||||
list.insertHead(5);
|
||||
list.insertHead(7);
|
||||
list.insertHead(10);
|
||||
list.insert(3);
|
||||
list.insertNth(1, 4);
|
||||
assert list.toString().equals("10->7->5->3->1");
|
||||
|
||||
/* Test search function */
|
||||
assert list.search(10) && list.search(5) && list.search(1) && !list.search(100);
|
||||
|
||||
/* Test get function */
|
||||
assert list.getNth(0) == 10 && list.getNth(2) == 5 && list.getNth(4) == 1;
|
||||
|
||||
/* Test delete function */
|
||||
list.deleteHead();
|
||||
list.deleteNth(1);
|
||||
list.delete();
|
||||
assert list.toString().equals("7->3");
|
||||
|
||||
assert list.size == 2 && list.size() == list.count();
|
||||
|
||||
list.clear();
|
||||
assert list.isEmpty();
|
||||
|
||||
try {
|
||||
list.delete();
|
||||
assert false; /* this should not happen */
|
||||
} catch (Exception e) {
|
||||
assert true; /* this should happen */
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* This class is the nodes of the SinglyLinked List.
|
||||
* They consist of a value and a pointer to the node
|
||||
* after them.
|
||||
* This class is the nodes of the SinglyLinked List. They consist of a value and a pointer to the
|
||||
* node after them.
|
||||
*/
|
||||
class Node {
|
||||
/**
|
||||
* The value of the node
|
||||
*/
|
||||
int value;
|
||||
/** The value of the node */
|
||||
int value;
|
||||
|
||||
/**
|
||||
* Point to the next node
|
||||
*/
|
||||
Node next;
|
||||
/** Point to the next node */
|
||||
Node next;
|
||||
|
||||
Node() {
|
||||
Node() {}
|
||||
|
||||
}
|
||||
/**
|
||||
* Constructor
|
||||
*
|
||||
* @param value Value to be put in the node
|
||||
*/
|
||||
Node(int value) {
|
||||
this(value, null);
|
||||
}
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*
|
||||
* @param value Value to be put in the node
|
||||
*/
|
||||
Node(int value) {
|
||||
this(value, null);
|
||||
}
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
* @param value Value to be put in the node
|
||||
* @param next Reference to the next node
|
||||
*/
|
||||
Node(int value, Node next) {
|
||||
this.value = value;
|
||||
this.next = next;
|
||||
}
|
||||
/**
|
||||
* Constructor
|
||||
*
|
||||
* @param value Value to be put in the node
|
||||
* @param next Reference to the next node
|
||||
*/
|
||||
Node(int value, Node next) {
|
||||
this.value = value;
|
||||
this.next = next;
|
||||
}
|
||||
}
|
||||
|
Reference in New Issue
Block a user