Module-II (1)
Module-II (1)
the list. If the element is present in the list, then the process is
12
Examples of Decrease and Conquer
Decrease by one:
◦ Insertion sort
◦ Graph search algorithms:
DFS
BFS
Topological sorting
◦ Algorithms for generating permutations, subsets
Variable-size decrease
◦ Euclid’s algorithm
◦ Selection by partition
13
Basic Idea
14
Insertion Sort
Tosort array A[0..n-1], sort A[0..n-2] recursively and
then insert A[n-1] in its proper place among the sorted
A[0..n-2]
Usually implemented bottom up (nonrecursively)
Example: Sort 6, 4, 1, 8, 5
6|4 1 8 5
4 6|1 8 5
1 4 6|8 5
1 4 6 8|5
1 4 5 6 8
Pseudocode of Insertion Sort
Decrease by One:
Insertion Sort
Insertion Sort
Algorithm to sort n elements:
Sort n-1 elements of the array
Insert the n-th element
17
Analysis of Insertion Sort
Time efficiency
Cworst(n) = n(n-1)/2 Θ(n2)
Cavg(n) ≈ n2/4 Θ(n2)
Cbest(n) = n - 1 Θ(n) (also fast on almost sorted arrays)
Stability: yes
a problem of size n
subproblem 1 subproblem 2
of size n/2 of size n/2
a solution to a solution to
subproblem 1 subproblem 2
a solution to
the original problem
Divide and Conquer Examples
Sorting: mergesort and quicksort
Tree traversals
Binary search
Mergesort(A,lb,ub)
{
If(lb<ub)
{
Mid=(lb+ub)/2;
Mergesort(A,lb,mid);
Mergesort(A,mid+1,ub);
Merge(A,lb,mid,ub);
}
Merge Algorithm
Merge(A,lb,mid,ub) If(i>mid)
{ {
I=lb; While(j<=ub)
j=mid+1; {
k=lb; b[k]=a[j];
while(i<=mid&& j<=ub) j++;
{ k++;
If(a[i]<=a[j]) }
{ else
b[k]=a[i]; While(i<=mid)
i++; {
} b[k]=a[i];
else i++;
{ k++;
b[k]=a[j]; }
j++; For(k=lb;k<=ub;k++)
} {
K++; a[k]=b[k];
} }
}
Mergesort Examples
83297154
72164
Merge Sort
General Divide and Conquer recurrence
A[i]≤p A[i] ≥ p
The Quicksort Algorithm
ALGORITHM Quicksort(A[l..r])
//Sorts a subarray by quicksort
//Input: A subarray A[l..r] of A[0..n-1],defined by its
left and right indices l and r
//Output: The subarray A[l..r] sorted in nondecreasing
order
if l < r
s Partition (A[l..r]) // s is a split position
Quicksort(A[l..s-1])
Quicksort(A[s+1..r]
The Partition Algorithm
ALGORITHM Partition (A[l ..r])
//Partitions a subarray by using its first element as a pivot
//Input: A subarray A[l..r] of A[0..n-1], defined by its left and right indices l and r (l <
r)
//Output: A partition of A[l..r], with the split position returned as this function’s value
P A[l]
i l; j r + 1;
Repeat
repeat i i + 1 until A[i]>=p //left-right scan
repeat j j – 1 until A[j] <= p//right-left scan
if (i < j) //need to continue with the scan
swap(A[i], a[j])
until i >= j //no need to scan
swap(A[l], A[j])
return j
Quicksort Example
i j
P A[l]
L=0,r=7, if(0<7) true i l; j r + 1;
Repeat
Pivot= A[l] = 15 repeat i i + 1 until A[i]>=p
repeat j j – 1 until A[j] <= p
i=0, j=8 if (i < j)
swap(A[i], a[j])
until i >= j
//no need to scan
swap(A[l], A[j])
return j
P=15
i j
A[i]>=p false so increment i value
i j
i j
A[j] <= p False so decrement j value
i j
A[j] <= p False so decrement j value
i j
A[j] <= p True so place j value
P=15
i j
If 1< 5 true so swap A[i] and A[j]
0 1 2 3 4 5 6 7
15 10 13 27 12 22 20 25
i j
i j
A[i]>=p false so increment i value
0 1 2 3 4 5 6 7
15 10 13 27 12 22 20 25
i j
A[i]>=p
true so place i value
0 1 2 3 4 5 6 7
15 10 13 27 12 22 20 25
i j
A[j] <= p True so place j value
0 1 2 3 4 5 6 7
15 10 13 27 12 22 20 25
i j
i j
ij
A[i]>=p true so place i value
0 1 2 3 4 5 6 7
15 10 13 12 27 22 20 25
ij
A[j] <= p False so decrement j value
0 1 2 3 4 5 6 7
Here i >j so
15 10 13 12 27 22 20 25 swap a[l]
and a[j]
j i
0 1 2 3 4 5 6 7
12 10 13 15 27 22 20 25
0 1 2
12 10 13
i j
ij
A[i]>=p true so place i value
0 1 2
12 10 13 P=12
ij
0 1 2
12 10 13
j i
0 1 2
10 12 13
4 5 6 7
27 22 20 25 P= 27
Efficiency of Quicksort
of the interval, We discard the second half of the list and recursively repeat the
process for the first half of the list by calculating the new middle and last element.
If the search Element (the item to be searched) is greater than the item in the
middle of the interval, we discard the first half of the list and work recursively on
the second half by calculating the new beginning and middle element.
Repeatedly, check until the value is found or interval is empty.
Binary Search
Binary Search – an Iterative Algorithm
ALGORITHM BinarySearch(A[0..n-1], K)
//Implements nonrecursive binary search
//Input: An array A[0..n-1] sorted in ascending order and
// a search key K
//Output: An index of the array’s element that is equal to K
// or –1 if there is no such element
l 0, r n – 1
while l r do //l and r crosses over can’t find K.
m (l + r) / 2
if K = A[m] return m //the key is found
else
if K < A[m] r m – 1 //the key is on the left half of the array
else lm+1 // the key is on the right half of the array
return -1
Binary Search -- Efficiency
Efficiency
C(n) Θ( log n)
Graph Traversal
moving on to nodes at the next depth level, while DFS explores the
deepest vertices of a graph before backtracking to explore other
vertices.
Graph traversal is used in many graph algorithms, such as finding the
Step 2: Start traversal from starting point and put it into the Queue
Empty.
Step 7 - When stack is empty, remove unused graph
Step 1: Select the vertex 1 as a starting point (Visit 1). Push 1 into the Stack
Step 2: Visit any non-visited adjacent vertex of 1. Push 2 in
the stack
Step 3: Visit any non-visited adjacent vertex
of 2. Push 3 in the stack
Step 4: There is no vertex to visit from 3. Now
Backtrack from 3 and POP 3 from Stack
Step 5: Visit any non-visited
adjacent vertex of 2. Push 5 in the stack.
Step 6: Visit any non-visited adjacent vertex of 5. Push 4 in the
stack.
Step 7: There is no unvisited vertex from 4. Now
start backtracking and POP 4 from stack.
Step 8: There is no unvisited vertex from 5.
Now start backtracking and POP 5 from stack.
Step 9: There is no unvisited vertex from 2. Now start
backtracking and POP 2 from stack.
Step 10: There is no unvisited
vertex from 1. POP 1 from stack.
Step 11: Stack is empty now. Stop DFS Traversal.
Final Spanning tree after DFS traversal is given
below
Graph Traversal
74
Pseudocode of DFS
Example: DFS traversal of undirected graph
a b c d
e f g h
1 2 6 7
a b c d
abgcdh
abgcd
abgcd
abgc
abfe
abg
abf
abf
e f g h
ab
ab
…
a
4 3 5 8
Red edges are tree
edges and white edges
are back edges.
Graph Search: DFS
77
DFS
DFS can be implemented with graphs represented as:
◦ adjacency matrices: Θ(|V|2). Why?
◦ adjacency lists: Θ(|V|+|E|). Why?
Applications:
◦ checking connectivity, finding connected components
◦ checking acyclicity (if no back edges)
◦ finding articulation points and biconnected components
◦ searching the state-space of problems for solutions (in AI)