0% found this document useful (0 votes)
22 views16 pages

ADS&A

Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as DOCX, PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
22 views16 pages

ADS&A

Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as DOCX, PDF, TXT or read online on Scribd
You are on page 1/ 16

1. Operations of double linked lists ?

Doubly linked list is a data structure that has reference to both the previous and next nodes in
the list. It provides simplicity to traverse, insert and delete the nodes in both directions in a list.
In a doubly linked list, each node contains three data members:
 data: The data stored in the node
 next: It refers to the reference to the next node
 prev: It refers to the reference to the previous node
Creation of Doubly Linked Lists in Java:
To create a doubly linked list, first, we need to define a Node class that has three data members
that will store the data stored in the node, the reference to the next node, and the reference to
the previous node.

public class Node {


int data;
Node prev;
Node next;
public Node(int data)
{
this.data = data;
this.prev = null;
this.next = null;
}
}

Now we need to create a doubly linked list class that will contain two variables head and tail
which will be referenced to the first and last node of the list respectively and also a constructor
which will initialize both head and tail to the null.

public class DoublyLinkedList {


Node head;
Node tail;
public DoublyLinkedList()
{
this.head = null;
this.tail = null;
}
}

Traversing a Doubly Linked List in Java:


To traverse in a doubly linked list, we will start from the head node and follow the next
reference until we reach the end of the list similarly, we can also start from the tail node and
follow the prev until we reach the head of the node.
Below is the code to traverse a linked list:

// Traversing from head to the end of the list


public void traverseForward()
{
Node current = head;
while (current != null) {
System.out.print(current.data + " ");
current = current.next;
}
}
// Traversing from tail to the head
public void traverseBackward()
{
Node current = tail;
while (current != null) {
System.out.print(current.data + " ");
current = current.prev;
}
}

Insertion in a Doubly Linked List in Java:


To insert a node in a doubly linked list, first, we will need to create a new node that is going to
be inserted and update the references of the adjacent nodes to add the new node and will
update the head or tail of the list if the new node is being inserted at the beginning or end of
the list.
A node can be added to a Doubly Linked List in three ways:
 Insertion at the beginning of the list
 Insertion at a specific position in the list
 Insertion at the end of the list
1) Insertion at the beginning of the list:
Create a new node to be inserted. Set the next pointer of the new node to the current head of
the doubly linked list. Set the previous pointer of the new node to null, as it will be the new
head. If the doubly linked list is not empty (i.e., the current head is not null), set the previous
pointer of the current head to the new node.

Insertion at the beginning of the list

Below is the code to insert a node at the front of the linked list:

public void insertAtBeginning(int data)


{
Node temp = new Node(data);
if (head == null) {
head = temp;
tail = temp;
}
else {
temp.next = head;
head.prev = temp;
head = temp;
}
}

2) Insertion at a specific position in the list:


Create a new node with the data to be inserted. Set the next pointer of the new node to the next
node of the node at given position. Set the previous pointer of the new node to the node at
given position. Set the next pointer of the node at the given position to the new node. If the
next node of the new node is not null, set its previous pointer to the new node.

Insertion at a specific position in the list

Below is the code to insert a node at a specific position in the linked list:

public void insertAtPosition(int data, int position)


{
Node temp = new Node(data);
if (position == 1) {
insertAtBeginning(data);
}
else {
Node current = head;
int currPosition = 1;
while (current != null && currPosition < position) {
current = current.next;
currPosition++;
}
if (current == null) {
insertAtEnd(data);
}
else {
temp.next = current;
temp.prev = current.prev;
current.prev.next = temp;
current.prev = temp;
}
}
}

3) Insertion at the end of the list:


First, we create a new node temp with the given data and then we will check if the list is empty
or not. If it is empty then we will set both the head and tail to the new node temp, and if the list
is not empty, traverse to the last node of the doubly linked list. Set the next pointer of the last
node to the new node. Set the previous pointer of the new node to the current last node. Set the
next pointer of the new node to null, as it will be the last node in the list.

Insertion at the end of the list

Below is the code to insert a node at the end of the linked list:

public void insertAtEnd(int data)


{
Node temp = new Node(data);
if (tail == null) {
head = temp;
tail = temp;
}
else {
tail.next = temp;
temp.prev = tail;
tail = temp;
}
}

Deletion in a Doubly Linked List in Java:


To delete a node in a doubly linked list, first, we need to update the references of the adjacent
nodes to delete the node and will update the head or tail of the list if the new node is being
inserted at the beginning or end of the list.
The deletion of a node in a doubly-linked list can be divided into three main categories:
 Deletion of the first node in the list.
 Deletion of a node at a specific position in the list.
 Deletion of the last node in the list.
Example:
1) Deletion of the first node in the list:

First, we will check if the list is empty if it is then we return, and if there is only one node in
the list then we will set both the head and tail to null otherwise we will simply set the head
node to the next node of the current head in the list, and set the previous reference of the new
head node to null.

 After the deletion of the first node.

Deletion of the first node in the list

Below is the code of Deletion of the first node in the list:


Java

public void deleteAtBeginning()


{
if (head == null) {
return;
}
if (head == tail) {
head = null;
tail = null;
return;
}
Node temp = head;
head = head.next;
head.prev = null;
temp.next = null;
}

2) Deletion of a node at a specific position in the list:


If the given position is 1 (i.e., the first node), update the head of the doubly linked list to be the
next node of the current head. Traverse to the node at the given position, keeping track of the
previous node. Set the next pointer of the previous node to the next node of the node to be
deleted. If the next node of the node to be deleted is not null, set its previous pointer to the
previous node. Delete the node.
 After the deletion of the 2nd node.

Deletion of a node at a specific position in the list

Below is the code of Deletion of a node at a specific position in the list:


Java

public void delete(int pos)


{
if (head == null) {
return;
}

if (pos == 1) {
deleteAtBeginning();
return;
}

Node current = head;


int count = 1;
while (current != null && count != pos) {
current = current.next;
count++;
}
if (current == null) {
System.out.println("Position wrong");
return;
}
if (current == tail) {
deleteAtEnd();
return;
}
current.prev.next = current.next;
current.next.prev = current.prev;
current.prev = null;
current.next = null;
}

3) Deletion of the last node in the list:


First, we will check if the list is empty if it is then we return, and if there is only one node in
the list then we will set both the head and tail to null otherwise we will simply set the tail node
to the previous node of the current tail node in the list, set the prev of the current tail node as
null and set the next reference of the new tail node to null.

Deletion of the last node in the list

Below is the code for the Deletion of the last node in the list:
Java

public void deleteAtEnd()


{
if (tail == null) {
return;
}
if (head == tail) {
head = null;
tail = null;
return;
}
Node temp = tail;
tail = tail.prev;
tail.next = null;
temp.prev = null;
}

2. What is a binary tree? Differentiate a binary tree from a binary search tree.

First, we will understand the binary tree and binary search tree separately, and then we will look
at the differences between a binary tree and a binary search tree.

What is a Binary tree?

A Binary tree is a non-linear data structure in which a node can have either 0, 1 or maximum 2
nodes. Each node in a binary tree is represented either as a parent node or a child node. There
can be two children of the parent node, i.e., left child and right child.

There is only one way to reach from one node to its next node in a binary tree.

A node in a binary tree has three fields:


o Pointer to the left child: It stores the reference of the left-child node.
o Pointer to the right child: It stores the reference of the right-child node.
o Data element: The data element is the value of the data which is stored by the node.

The binary tree can be represented as:

In the above figure, we can observe that each node contains utmost 2 children. If any node does
not contain left or right child then the value of the pointer with respect to that child would be
NULL.

Basic terminologies used in a Binary tree are:

o Root node: The root node is the first or the topmost node in a binary tree.
o Parent node: When a node is connected to another node through edges, then that node is
known as a parent node. In a binary tree, parent node can have a maximum of 2 children.
o Child node: If a node has its predecessor, then that node is known as a child node.
o Leaf node: The node which does not contain any child known as a leaf node.
o Internal node: The node that has atleast 2 children known as an internal node.
o Depth of a node: The distance from the root node to the given node is known as a depth
of a node. We provide labels to all the nodes like root node is labeled with 0 as it has no
depth, children of the root nodes are labeled with 1, children of the root child are labeled
with 2.
o Height: The longest distance from the root node to the leaf node is the height of the
node.

In a binary tree, there is one tree known as a perfect binary tree. It is a tree in which all the
internal nodes must contain two nodes, and all the leaf nodes must be at the same depth. In the
case of a perfect binary tree, the total number of nodes exist in a binary tree can be calculated by
using the following equation:
n = 2m+1-1

where n is the number of nodes, m is the depth of a node.

What is a Binary Search tree?

A Binary search tree is a tree that follows some order to arrange the elements, whereas the binary
tree does not follow any order. In a Binary search tree, the value of the left node must be smaller
than the parent node, and the value of the right node must be greater than the parent node.

Let's understand the concept of a binary search tree through examples.

In the above figure, we can observe that the value of the root node is 15, which is greater than the
value of all the nodes in the left subtree. The value of root node is less than the values of all the
nodes in a right-subtree. Now, we move to the left-child of the root node. 10 is greater than 8 and
lesser than 12; it also satisfies the property of the Binary search tree. Now, we move to the right-
child of the root node; the value 20 is greater than 17 and lesser than 25; it also satisfies the
property of binary search tree. Therefore, we can say that the tree shown above is the binary
search tree.

Now, if we change the value of 12 to 16 in the above binary tree, we have to find whether it is
still a binary search tree or not.

The value of the root node is 15 which is greater than 10 but lesser than 16, so it does not satisfy
the property of the Binary search tree. Therefore, it is not a binary search tree.

Operations on Binary search tree


We can perform insert, delete and search operations on the binary search tree. Let's understand
how a search is performed on a binary search. The binary tree is shown below on which we have
to perform the search operation:

Suppose we have to search 10 in the above binary tree. To perform the binary search, we will
consider all the integers in a sorted array. First, we create a complete list in a search space, and
all the numbers will exist in the search space. The search space is marked by two pointers, i.e.,
start and end. The array of the above binary tree can be represented as

First, we will calculate the middle element and compare the middle element with the element,
which is to be searched. The middle element is calculated by using n/2. The value of n is 7;
therefore, the middle element is 15. The middle element is not equal to the searched element, i.e.,
10.

Note: If the element is being searched is lesser than the mid element, then the searching will
be performed in the left half; else, searching will be done on the right half. In the case of
equality, the element is found.

As the element to be searched is lesser than the mid element, so searching will be performed on
the left array. Now the search is reduced to half, as shown below:

The mid element in the left array is 10, which is equal to the searched element.

Time complexity
In a binary search, there are n elements. If the middle element is not equal to the searched
element, then the search space is reduced to n/2, and we will keep on reducing the search space
by n/2 until we found the element. In the whole reduction, if we move from n to n/2 to n/4 and so
on, then it will take log2n steps.

Differences between Binary tree and Binary search tree

Basis for Binary tree Binary search tree


comparison

Definition A binary tree is a non-linear data


A binary search tree follows some order to
structure in which a node can have
arrange the elements. In a Binary search
utmost two children, i.e., a node can
tree, the value of left node must be smaller
have 0, 1 or maximum two children.
than the parent node, and the value of
A binary search tree is an ordered
right node must be greater than the parent
binary tree in which some order is
node. This rule is applied recursively to
followed to organize the nodes in a
the left and right subtrees of the root.
tree.

Structure The structure of the binary tree is The binary search tree is one of the
that the first node or the topmost types of binary tree that has the value of
node is known as the root node. all the nodes in the left subtree lesser or
Each node in a binary tree contains equal to the root node, and the value of
the left pointer and the right pointer. all the nodes in a right subtree are
The left pointer contains the address greater than or equal to the value of the
of the left subtree, whereas right root node.
pointer contains the address of right
subtree.

Operations The operations that can be Binary search trees are the sorted binary
implemented on a binary tree are trees that provide fast insertion, deletion
insertion, deletion, and traversal. and search. Lookups mainly implement
binary search as all the keys are
arranged in sorted order.

types Four types of binary trees are Full There are different types of binary
Binary Tree, Complete Binary Tree, search trees such as AVL trees, Splay
Perfect Binary Tree, and Extended tree, Tango trees, etc.
Binary Tree.

3. Linear Probing:

It is a Scheme in Computer Programming for resolving collision in hash tables.

Suppose a new record R with key k is to be added to the memory table T but that the memory
locations with the hash address H (k). H is already filled.
Our natural key to resolve the collision is to crossing R to the first available location following T
(h). We assume that the table T with m location is circular, so that T [i] comes after T [m].

The above collision resolution is called "Linear Probing".

Linear probing is simple to implement, but it suffers from an issue known as primary clustering.
Long runs of occupied slots build up, increasing the average search time. Clusters arise because
an empty slot proceeded by i full slots gets filled next with probability (i + 1)/m. Long runs of
occupied slots tend to get longer, and the average search time increases.

Given an ordinary hash function h': U {0, 1...m-1}, the method of linear probing uses the hash
function.

h (k, i) = (h' (k) + i) mod m

Where 'm' is the size of hash table and h' (k) = k mod m. for i=0, 1....m-1.

Given key k, the first slot is T [h' (k)]. We next slot T [h' (k) +1] and so on up to the slot T [m-1].
Then we wrap around to slots T [0], T [1]....until finally slot T [h' (k)-1]. Since the initial probe
position dispose of the entire probe sequence, only m distinct probe sequences are used with
linear probing.

Example: Consider inserting the keys 24, 36, 58,65,62,86 into a hash table of size m=11 using
linear probing, consider the primary hash function is h' (k) = k mod m.

Solution: Initial state of hash table

Insert 24. We know h (k, i) = [h' (k) + i] mod m


Now h (24, 0) = [24 mod 11 + 0] mod 11
= (2+0) mod 11 = 2 mod 11 = 2
Since T [2] is free, insert key 24 at this place.

Insert 36. Now h (36, 0) = [36 mod 11 + 0] mod 11


= [3+0] mod 11 = 3
Since T [3] is free, insert key 36 at this place.

Insert 58. Now h (58, 0) = [58 mod 11 +0] mod 11


= [3+0] mod 11 =3
Since T [3] is not free, so the next sequence is
h (58, 1) = [58 mod 11 +1] mod 11
= [3+1] mod 11= 4 mod 11=4
T [4] is free; Insert key 58 at this place.
Insert 65. Now h (65, 0) = [65 mod 11 +0] mod 11
= (10 +0) mod 11= 10
T [10] is free. Insert key 65 at this place.

Insert 62. Now h (62, 0) = [62 mod 11 +0] mod 11


= [7 + 0] mod 11 = 7
T [7] is free. Insert key 62 at this place.

Insert 86. Now h (86, 0) = [86 mod 11 + 0] mod 11


= [9 + 0] mod 11 = 9
T [9] is free. Insert key 86 at this place.
Thus,

4. Bubble sort

In this article, we will discuss the Bubble sort Algorithm. The working procedure of bubble sort
is simplest. This article will be very helpful and interesting to students as they might face bubble
sort as a question in their examinations. So, it is important to discuss the topic.

Bubble sort works on the repeatedly swapping of adjacent elements until they are not in the
intended order. It is called bubble sort because the movement of array elements is just like the
movement of air bubbles in the water. Bubbles in water rise up to the surface; similarly, the array
elements in bubble sort move to the end in each iteration.

Although it is simple to use, it is primarily used as an educational tool because the performance
of bubble sort is poor in the real world. It is not suitable for large data sets. The average and
worst-case complexity of Bubble sort is O(n2), where n is a number of items.

Bubble short is majorly used where -

o complexity does not matter


o simple and shortcode is preferred

Algorithm

In the algorithm given below, suppose arr is an array of n elements. The assumed swap function
in the algorithm will swap the values of given array elements.

1. begin BubbleSort(arr)
2. for all array elements
3. if arr[i] > arr[i+1]
4. swap(arr[i], arr[i+1])
5. end if
6. end for
7. return arr
8. end BubbleSort

Working of Bubble sort Algorithm

Now, let's see the working of Bubble sort Algorithm.

To understand the working of bubble sort algorithm, let's take an unsorted array. We are taking a
short and accurate array, as we know the complexity of bubble sort is O(n2).

Let the elements of array are -

First Pass

Sorting will start from the initial two elements. Let compare them to check which is greater.

Here, 32 is greater than 13 (32 > 13), so it is already sorted. Now, compare 32 with 26.

Here, 26 is smaller than 36. So, swapping is required. After swapping new array will look like -

Now, compare 32 and 35.


Here, 35 is greater than 32. So, there is no swapping required as they are already sorted.

Now, the comparison will be in between 35 and 10.

Here, 10 is smaller than 35 that are not sorted. So, swapping is required. Now, we reach at the
end of the array. After first pass, the array will be -

Now, move to the second iteration.

Second Pass

The same process will be followed for second iteration.

Here, 10 is smaller than 32. So, swapping is required. After swapping, the array will be -

Now, move to the third iteration.

Third Pass

The same process will be followed for third iteration.


Here, 10 is smaller than 26. So, swapping is required. After swapping, the array will be -

Now, move to the fourth iteration.

Fourth pass

Similarly, after the fourth iteration, the array will be -

Hence, there is no swapping required, so the array is completely sorted.

You might also like