Data Structures and Algorithms
Data Structures and Algorithms
Data Structures and Algorithms
Example:
Data type is a way to classify various type of data such as integer, string, etc. which determines the
values that can be used with the corresponding type of data, the type of operations that can be
performed on the corresponding type of data.
Those data types for which a language has built-in support are known as Built- in Data types. For
example, most the languages provide the following built-in data types.
Integers
Boolean (true, false)
Floating (decimal numbers)
Character and Strings
Those data types which are implementation independent as they can be implemented in one or the
other way are known as derived data types. These data types are normally built by the combination of
primary or built-in data types and associated operations on them.
For example:
List
Array
Stack
Queue
Basic operations
The data in the data structures are processed by certain operations. The particular data structure chosen
largely depends on the frequency of the operation that needs to be performed on the data structure.
Traversing
Searching
Insertion
Deletion
Sorting
Merging
Array – is a container which can hold a fix number of items and these items should be of the same type.
Most of the data structures make use arrays to implement their algorithms.
Array Representation
Arrays can be declared in various ways in different languages. For illustration, let’s take C array
declaration.
Int array [10] = {35, 33, 42, 10, 14,19, 27, 44, 26, 31}
Arrays can be declared in various ways in different languages. For illustration, let’s take C array
declaration.
35 33 42 10 14 19 27 44 26 31
0 1 2 3 4 5 6 7 8 9
Index
As per the above illustration, following are the important points to be considered .
Basic operations
Insertion operation – insert operation is to insert one or more data elements into an array. Based on the
requirement, a new element can be added at the beginning, end, or any given index of array.
Deletion operation – refers to removing an existing element from the array and re-organizing all
elements of an array.
Search operation – you can perform a search of an array element based on its value or its index.
Update operation – update operation refers to updating an existing element from the array at a given
index
Linked List – is a sequence of links which contains items. Each link contains a connection to another link.
Linked list is the second most – used data structure after array. Following are the important terms to
understand the concept of Linked List.
Link – each link of a linked list can store a data called an element
Next – each link of a linked list contains a link to the next link called next.
LinkedList - a linked list contains the connection link to the first link called first.
Linked list can be visualized as a chain of nodes, where every node points to the next node.
Basic operations
Insertion operation
Adding a new node in linked list is a more than one step activity. We shall learn this with diagrams
here. First, create a node using the same structure and find the location where it has to be inserted.
Imagine that we are inserting a node B (NewNode), between A (leftnode) and C (rightnode). Then
point B next to C.
This will put the new node in the middle of the two . the new list should like this
Similar steps should be taken if the node is being inserted at the beginning of the list. While
inserting it at the end, the second last node of the list should point to the new node and the new
node will point to NULL.
Deletion operation
Deletion is also a more than one step process. We shall learn with pictorial representation. First,
locate the target node to be removed, by using searching algorithms.
The left (previous) node of the target node now should point to the next node of the target node-
LeftNode next → TargetNode
This will remove the link that was pointing to the target node. Now, using the following code, we will
remove what the target node is pointing at.
TargetNode.next→ Null
We need to use the deleted node. We can keep that in memory otherwise we can simply deallocate
memory and wipe off the target node completely.
Reverse operation
this operation is a through one. We need to make the last node to be pointed by the head node and
reverse the whole linked list.
First, we traverse to the end of the list. It should be pointing to NULL. Now, we shall make it point to
its previous node-
We have to make sure that the last node is not the last node. So we’ll have some temp node, which
looks like the head node pointing to that last node. Now, we shall make all left side nodes point to
their previous nodes one by one.
Except the node (first node ) pointed by the head node, all nodes should point to their, predecessor,
making them their new successor. The first node will point to NULL.
We’ll make the head node point to the new first node by using the temp node.
A stack is an Abstract Data Type (ADT), commonly used in most programming languages. It is named
stack as it behaves like a real-world stack, for example – a deck of cards or a pile of plates, etc.
A real world stack allows operations at one end only. For example, we can place or remove a card or
plate from the top of the stack only. Likewise, Stack ADT allows all data operations at one end only.
At any given time, we can only access the top element of a stack.
This feature makes it LIFO data structure. LIFO stands for Last-in- firs- out. Here, the element which
is placed (inserted or added) last, is accessed first. In stack terminology, insertion operation is called
PUSH operation and removal operation is called POP operation.
Stact Representation
A stack can be implemented by means Array, Structure, Pointer, and Linked List. Stack can either be
a fixed size one or it may have a sense of dynamic resizing. Here, we are going to implement stack
using arrays, which makes it a fixed size stack implementation.
Basic operations
Stack operations may involve initializing the stack, using it and then de- initializing it. Apart from
these basic stuffs, a stack is used for the following two primary operations.
To use a stack efficiently, we need to check the status of stack as well. For the same purpose, the
following functionality is added to stacks.
Peek()-get the tod data element of the stack, without removing it.
isFull()-check if stack is full
isEmpty- check if stack is empty
At all times, we maintain a pointer to the last PUSHed data on the stack. As this pointer always
represents the top of the stack, hence named top. The top pointer provides top value of the stack
without actually removing it.
end procedure
Example:
int peek () {
isFull ()
return true
else
return false,
bool isfull () {
If (top == MAXSIZE)
return true;
else
return false;
isempty ()
else
return false
endif
end procedure
bool isempty(){
if(top == -1)
return true;
else
return false;
Push operation
The process of putting a new data element onto stack is known as a Push operation.
if stack is full
return null
endif
top←top + 1
stack [top]←data
end procedure
if(!isFull()){
stack[top] =data;
}else{
printf(“could not insert data, Stack is full.\n”);
}
}
POP Operation
Accessing the content while removing it from the stack, is know as pop operation. In array
implementation of pop() operation, the data element is not actually removed, instead top is
decremented to a lower position in the stack to point to the next value. But in linked list
implementation, pop () actually removes the data element and deallocates memory space .
if stack is empty
return null
endif
data ←stack[top]
top← top-1
return data
end procedure
Data Structure – Expressing Parsing
The way to write arithmetic expression is known as a notation. An arithmetic expression can be
written in three different but equivalent notations, i.e., without changing the essence or output of
an expression.
Infix Notation
Prefix (Polish) Notation
Postfix (Reverse-Polish) Notation
Infix Notation
We write expression in infix notation, e.g. a – b + c, where operators are used in between operands. It is
easy for us humans to read, write, and speak in infix notation but the same does not go well with
computing devices. An algorithm to process infix notation could be difficult and costly in terms of time
and space consumption.
Prefix Notation
In this notation, operator is prefixed to operands, i.e. operator is written ahead of operands. For
example, +ab. This is equivalent to its infix notation a + b. Prefix notation also known as Polish
Notation.
Postfix Notation
This notation style is known as Reversed Polish Notation. In this notation style, the operator is
postfixed to the operands i.e.,the operator is written after the operands.
2 (a + b) ∗ c ∗+abc ab+c∗
3 a ∗ (b + c) ∗a+bc abc+∗
5 (a + b) ∗ (c + d) ∗+ab+cd ab+cd+∗
As we have discussed, it is not a very efficient way to design an algorithm or program to parse infix
notations. Instead, these infix notations are first converted into either postfix r prefix notations and
then computed.
To parse any arithmetic expression, we need to take care of operator precedence and associativity
also.
Precedence
When an operand is in between two different operators, which operator will take the operand first,
is decided by the precedence of an operator over others. For example:
As multiplication operation has precedence over addition, b*c will be evaluated first. A table of operator
precedence is provided later.
Associativity
Associativity describes the rule where operators with the same precedence appear in an expression. For
example a + b –c , both + and - have the same precedence, the then which part of the expression will
be evaluated first, is determined by associativity of those operators. Here, both + and – are left
associative, so the expression will be evaluated as (a+b)-c.
The above table shows the default behavior of operators. At any point of time in
expression evaluation, the order can be altered by using parenthesis. For example −
In a + b*c, the expression part b*c will be evaluated first, with multiplication as
precedence over addition. We here use parenthesis for a + b to be evaluated first,
like (a + b)*c.