DAA RECORD

Download as pdf or txt
Download as pdf or txt
You are on page 1of 63

(Approved by AICTE, Affiliated to Anna University & Accredited by NBA)

Chittoor Main Road, Vellore - 632059

DEPAPTMENT OF COMPUTER SCIENCE AND BUSINESS SYSTEM

AD 3351 – DESIGN AND ANALYSIS OF ALGORITHM


LABORATORY
RECORD

Submitted by

Name :
Register No :
Semester/year :
Department :
EX: 1 A Implement recursive and non-recursive algorithm and
DATE: study the order of growth from logn to n!

AIM:

ALGORITHM:

PROGRAM:
Recursive algorithm:
def factorial(n):
if (n == 1 or n == 0):
return 1
else:
return (n * factorial(n - 1))
num = 5
print("number: ", num)
print("Factorial: ", factorial(num))

Output:
number: 5
Factorial: 120

Order of growth: O(n!)


EX: 1A
Non-recursive algorithm:
n = int(input("Enter number:"))
fact = 1
while n > 0:
fact = fact * n
n=n-1
print("Factorial of the number is:")
print(fact)

Output:
Enter the number:5
Factorial of the number:120

Order of growth: O(n)


RESULT:
EX: 1B
DATE: Implementation of Linear Search

AIM:

ALGORITHM:
EX: 1B
Program (Linear Search):
import time
import matplotlib.pyplot as plt # Plotting the graph
def linear_search(arr, x):
for i in range(len(arr)):
if arr[i] == x:
return i
return -1
def measure_time(n):
arr = [i for i in range(n)]
start_time = time.time()
linear_search(arr, n + 1)
return time.time() - start_time
def time_taken(arr, x):
start_time = time.time()
linear_search(arr, x)
return time.time() - start_time
if __name__ == '__main__':
n_values = [10, 100, 1000, 10000, 100000, 1000000]
times = [measure_time(n) for n in n_values]
print(n_values)
print(times)
# Example usage of time_taken function
arr = [i for i in range(1000000)]
x = 999999
print(f"Time taken to find {x} in arr using linear search: {time_taken(arr, x)} seconds")

plt.plot(n_values, times)
plt.xlabel('n - number of elements in list')
plt.ylabel('Time taken (in seconds)')
plt.title('Linear search performance')
plt.show()

OUTPUT:
[10, 100, 1000, 10000, 100000, 1000000]
[2.6226043701171875e-06, 7.867813110351562e-06, 0.0027456283569335938,
0.000804901123046875, 0.028525352478027344, 0.10596990585327148]
Time taken to find 999999 in arr using linear search: 0.07597494125366211 seconds
RESULT:
EX: 1C

DATE: Implement recursive Binary Search

AIM:

ALGORITHM:
EX: 1C
Program (Binary Search):
import time
import matplotlib.pyplot as plt
def binary_search_recursive(arr, x, left, right):
if right >= left:
mid = (left + right) // 2
if arr[mid] == x:
return mid
elif arr[mid] > x:
return binary_search_recursive(arr, x, left, mid-1)
else:
return binary_search_recursive(arr, x, mid+1, right)
else:
return -1
def measure_time(n):
arr = [i for i in range(1, n + 1)]
x = arr[-1] # searching for the last element
start = time.time()
binary_search_recursive(arr, x, 0, len(arr) - 1)
end = time.time()
return end - start
n_values = [10, 100, 1000, 10000, 100000, 1000000]
time_values = [measure_time(n) for n in n_values]
print(n_values)
print(time_values)
plt.plot(n_values, time_values)
plt.xscale('log')
plt.xlabel('Number of elements (log scale)'
plt.ylabel('Time taken (seconds)')
plt.title('Recursive Binary Search Performance')
plt.show()

Output:
[10, 100, 1000, 10000, 100000, 1000000]
[3.5762786865234375e-06, 3.337860107421875e-06, 6.9141387939453125e-06,
1.049041748046875e-05, 1.4543533325195312e-05, 2.1457672119140625e-05]
RESULT:
EX:2

DATE: Divide and Conquer-Strassen’s matrix multiplication

AIM:

ALGORITHM:

Program:
x = [[0, 2], [0, 1]]
print("Matrix x is:")
for i in range(len(x)):
print("\t", x[i])
y = [[0, 0], [3, 4]]
print("Matrix y is:")
for i in range(len(y)):
print("\t", y[i])
def strassen(a, b):
S = [b[0][1] - b[1][1],
EX: 2
a[0][0] + a[0][1],
a[1][0] + a[1][1],
b[1][0] - b[0][0],
a[0][0] + a[1][1],
b[0][0] + b[1][1],
a[0][1] - a[1][1],
b[1][0] + b[1][1],
a[0][0] - a[1][0],
b[0][0] + b[0][1]]
P = [a[0][0] * S[0],
S[1] * b[1][1],
S[2] * b[0][0],
a[1][1] * S[3],
S[4] * S[5],
S[6] * S[7],
S[8] * S[9]]
C = [[P[4] + P[3] - P[1] + P[5], P[0] + P[1]],
[P[2] + P[3], P[4] + P[0] - P[2] - P[6]]]
print("Strassen's Matrix multiplication of x and y is.")
print(S)
print(P)
print(C)
strassen(x, y)
Output:
matrix x is:
[0, 2]
[0, 1]
matrix y is:
[0, 0]
[3, 4]
Strassen's Matrix multiplication of x and y is.
[-4, 2, 1, 3, 1, 4, 1, 7, 0, 0]
[0, 8, 0, 3, 4, 7, 0]
[[6, 8], [3, 4]]
EX: 3

DATE: Decrease and conquer-Topological sorting

AIM:

ALGORITHM:
EX: 3
Program:
from collections import defaultdict
def topological_sort(vertices, edges):
sorted_order = []
in_degree = {vertex: 0 for vertex in vertices}
graph = defaultdict(list)
# Create the graph
for edge in edges:
src, dest = edge
graph[src].append(dest)
in_degree[dest] += 1
# Create a queue and add all vertices with 0 in-degree
queue = []
for vertex in in_degree:
if in_degree[vertex] == 0:
queue.append(vertex)
# Start the topological sort
while queue:
vertex = queue.pop(0)
sorted_order.append(vertex)
# Decrease in-degree for all neighbors
for neighbor in graph[vertex]:
in_degree[neighbor] -= 1
# Add to queue if in-degree becomes 0
if in_degree[neighbor] == 0:
queue.append(neighbor)
# Check for a cycle
if len(sorted_order) != len(vertices):
return [] # Cycle detected, no topological order possible
else:
return sorted_order
vertices = [1, 2, 3, 4, 5, 6]
edges = [(1, 2), (1, 5), (2, 3), (2, 5), (3, 4), (4, 6), (5, 6)]
print(topological_sort(vertices, edges))

Output:
[1, 2, 5, 3, 4, 6]
RESULT:
EX: 4

DATE: Sort a given set of elements using the Heap sort

AIM:

ALGORITHM:

Program (Heap sort):


import random
import time
import matplotlib.pyplot as plt
def heapify(arr, n, i):
largest = i
l=2*i+1
r=2*i+2
if l < n and arr[largest] < arr[l]:
largest = l
if r < n and arr[largest] < arr[r]:
largest = r
if largest != i: EX: 4

arr[i], arr[largest] = arr[largest], arr[i]

heapify(arr, n, largest)

def heap_sort(arr):

n = len(arr)

# Build max heap

for i in range(n // 2 - 1, -1, -1):

heapify(arr, n, i)

# Extract elements one by one

for i in range(n - 1, 0, -1):

arr[i], arr[0] = arr[0], arr[i]

heapify(arr, i, 0)

n_values = [1000, 2000, 3000, 4000, 5000]

times = []

for n in n_values:

arr = [random.randint(1, 10000) for _ in range(n)]

start_time = time.time()

heap_sort(arr)

end_time = time.time()

times.append(end_time - start_time)

plt.plot(n_values, times)

plt.xlabel('n')

plt.ylabel('Time (s)')

plt.title('Heap sort time complexity')

plt.show()
Output:

n=1000: 0.07786297798156738 seconds

n=2000: 0.32976579666137695 seconds

n=3000: 0.7329976558685303 seconds

n=4000: 1.3388376235961914 seconds

n=5000: 2.0903823375701904 seconds


RESULT:
EX:5A
DATE: Dynamic programming-coin change problem

AIM:

ALGORITHM:
EX: 5A
Program:
class Solution(object):
def coinChange(self, coins, amount):
if amount == 0:
return 0

if min(coins) > amount:

return -1
dp = [-1] + [float('inf')] * amount
for i in coins:
if i <= amount:
dp[i] = 1
for j in range(1, amount + 1):
for coin in coins:
if j - coin >= 0 and dp[j - coin] != float('inf'):
if dp[j] == -1:
dp[j] = dp[j - coin] + 1
else:
dp[j] = min(dp[j], dp[j - coin] + 1)
return dp[amount]
ob1 = Solution()
print(ob1.coinChange([1, 2, 5], 11))

Output:
3
RESULT:
EX: 5B Compute the transitive closure of a given directed graph
DATE: using Warshall's algorithm

AIM:

ALGORITHM:
EX: 5B
Program (Warshall's algorithm):
import time
import matplotlib.pyplot as plt
def transitiveClosure(graph):
V = len(graph)
reach = list(map(lambda i: list(map(lambda j: j, i)), graph))
for k in range(V):
for i in range(V):
for j in range(V):
reach[i][j] = reach[i][j] or (reach[i][k] and reach[k][j])
return reach
def time_taken(graph):
print("Computing transitive closure...")
start = time.time()
result = transitiveClosure(graph)
end = time.time()
print("Time taken:", end - start)
return result
# Example usage
graph = [[1, 1, 0, 1],
[0, 1, 1, 0],
[0, 0, 1, 1],
[0, 0, 0, 1]]
transitive_closure_result = time_taken(graph)
print("Transitive Closure Matrix:")
for row in transitive_closure_result:
print(row)
Output:
[[1, 1, 1, 1], [0, 1, 1, 1], [0, 0, 1, 1], [0, 0, 0, 1]]
Time taken to compute transitive closure: 2.4557113647460938e-05
RESULT:
EX: 5C Implement Floyd’s algorithm for the All-Pairs- Shortest-
DATE: problem

AIM:

ALGORITHM:
EX: 5C
Program (Floyd’s algorithm):
import time
import matplotlib.pyplot as plt
def floydWarshall(graph):
V = len(graph)
dist = list(map(lambda i: list(map(lambda j: j, i)), graph))
for k in range(V):
for i in range(V):
for j in range(V):
dist[i][j] = min(dist[i][j], dist[i][k] + dist[k][j])
return dist
def time_taken(graph):
print("Computing Floyd-Warshall...")
start_time = time.time()
result = floydWarshall(graph)
end_time = time.time()
print("Time taken:", end_time - start_time)
return result
graph = [[0, 5, 99999, 99999],
[50, 0, 15, 5],
[30, 99999, 0, 99999],
[15, 99999, 5, 0]]
floyd_warshall_result = time_taken(graph)
print("Shortest Distance Matrix:")
for row in floyd_warshall_result:
print(row)

Output:
[[0, 5, 15, 10], [20, 0, 10, 5], [30, 35, 0, 40], [15, 20, 5, 0]]
time of my program is 4.506111145019531e-05 sec
RESULT:
EX:5D
DATE: Dynamic Programming-Knapsack problem

AIM:

ALGORITHM:
EX: 5D
Program:
def knapSack(W, wt, val, n):
K = [[0 for x in range(W + 1)] for x in range(n + 1)]
for i in range(n + 1):
for w in range(W + 1):
if i == 0 or w == 0:
K[i][w] = 0
elif wt[i - 1] <= w:
K[i][w] = max(val[i - 1] + K[i - 1][w - wt[i - 1]], K[i - 1][w])
else:
K[i][w] = K[i - 1][w]
return K[n][W]
val = [60, 100, 120]
wt = [10, 20, 30]
W = 50
n = len(val)
print(knapSack(W, wt, val, n))

Output:
220
RESULT:
EX:6 A
DATE: Greedy Technique-Dijkstra’s algorithm

AIM:

ALGORITHM:
PROGRAM: EX: 6A

import heapq
import time
def dijkstra(graph, start):
distances = {vertex: float('infinity') for vertex in graph}
distances[start] = 0
priority_queue = [(0, start)]
while priority_queue:
current_distance, current_vertex = heapq.heappop(priority_queue)
if current_distance > distances[current_vertex]:
continue
for neighbor, weight in graph[current_vertex].items():
distance = current_distance + weight
if distance < distances[neighbor]:
distances[neighbor] = distance
heapq.heappush(priority_queue, (distance, neighbor))
return distances
def time_taken(graph, start):
print("Time taken by dijkstra function:")
start_time = time.time()
dijkstra(graph, start)
end_time = time.time()
return end_time - start_time
graph = {
'A': {'B': 1, 'C': 4}
'B': {'A': 1, 'C': 2, 'D': 5},
'C': {'A': 4, 'B': 2, 'D': 1},
'D': {'B': 5, 'C': 1}
}
start_node = 'A'
print(dijkstra(graph, start_node))
print("Time taken by dijkstra function: {} seconds".format(time_taken(graph, start_node)))

Output:
{'A': 0, 'B': 1, 'C': 3, 'D': 4}
Time taken by dijkstra function: 1.8596649169921875e-05 seconds
RESULT:
EX:6 B
DATE: Greedy Technique-Huffman Trees and codes

AIM:

ALGORITHM:
PROGRAM: EX: 6B

import heapq
import itertools
pq = []
entry_finder = {}
REMOVED = '<removed-task>'
counter = itertools.count()
def add_task(task, priority=0):
if task in entry_finder:
remove_task(task)
count = next(counter)
entry = [priority, count, task]
entry_finder[task] = entry
heapq.heappush(pq, entry)
def remove_task(task):
entry = entry_finder.pop(task)
entry[-1] = REMOVED
def pop_task():
while pq:
priority, count, task = heapq.heappop(pq)
if task is not REMOVED:
del entry_finder[task]
return task
raise KeyError('pop from an empty priority queue')
def inorder(root):
if root is not None:
inorder(root.left)
print(root.frequency)
inorder(root.right)
class Node():
def __init__(self, d, f):
self.data = d
self.frequency = f
self.left = None
self.right = None
def greedy_huffman():
while len(pq) > 1:
left = pop_task()
right = pop_task()
freq = left.frequency + right.frequency
z = Node(None, freq)
z.left = left
z.right = right
add_task(z, z.frequency)
return pop_task()
if __name__ == '__main__':
a = Node('a', 42)
b = Node('b', 20)
c = Node('c', 5)
d = Node('d', 10)
e = Node('e', 11)
f = Node('f', 12)
add_task(a, a.frequency)
add_task(b, b.frequency)
add_task(c, c.frequency)
add_task(d, d.frequency)
add_task(e, e.frequency)
add_task(f, f.frequency)
tree = greedy_huffman()
inorder(tree)

Output:
42
100
11
23
12
58
5
15
10
35
20
RESULT:
EX: 07
DATE: Iterative improvement-simplex method

AIM:

ALGORITHM:

PROGRAM:
from numpy import *

def simplex_method(A, b, c):


m, n = A.shape
B = arange(n, n+m)
N = arange(n)
x = zeros(n+m)
EX: 7
x[-m:] = b
while True:
# Find the entering variable
y = dot(c, A)
i = argmin(y)
if y[i] >= 0:
return x[:n]
# Find the leaving variable
ratios = dot(A.T, x[B])
j = argmin(ratios)
if ratios[j] <= 0:
return None
# Update the basis
x = x.astype(float) # Explicitly cast to float64
A = A.astype(float) # Explicitly cast to float64
x /= x[B[j]]
A /= A[:, j:j+1]
for r in range(m):
if r != j:
x[B[r]] -= x[B[j]] * A[r, j]
A[r] -= A[j] * A[r, j]
B[j], N[i] = N[i], B[j]
# Example usage
A = array([[1, 1], [3, 1]])
b = array([5, 15])
c = array([-4, -5])
result = simplex_method(A, b, c)
print(result)

Output:
None
RESULT:
EX: 8 A
DATE: Backtracking-N-Queen problem

AIM:

ALGORITHM:
EX: 8A
PROGRAM:
import time

def is_safe(board, row, col, N):


for x in range(col):
if board[row][x] == 1:
return False
for x, y in zip(range(row, -1, -1), range(col, -1, -1)):
if board[x][y] == 1:
return False
for x, y in zip(range(row, N, 1), range(col, -1, -1)):
if board[x][y] == 1:
return False
return True
def solve_n_queens(board, col, N):
if col >= N:
return True
for i in range(N):
if is_safe(board, i, col, N):
board[i][col] = 1
if solve_n_queens(board, col + 1, N):
return True
board[i][col] = 0
return False
def n_queens(N):
board = [[0 for x in range(N)] for y in range(N)]
start_time = time.time()
if not solve_n_queens(board, 0, N):
print("No solution exists")
return False
end_time = time.time()
print("Time taken: ", end_time - start_time)
return board
board = n_queens(8)
if board:
for row in board:
print(row)

Output:
[1, 0, 0, 0, 0, 0, 0, 0]
[0, 0, 0, 0, 0, 0, 1, 0]
[0, 0, 0, 0, 1, 0, 0, 0]
[0, 0, 0, 0, 0, 0, 0, 1]
[0, 1, 0, 0, 0, 0, 0, 0]
[0, 0, 0, 1, 0, 0, 0, 0]
[0, 0, 0, 0, 0, 1, 0, 0]
[0, 0, 1, 0, 0, 0, 0, 0]
RESULT:
EX: 8 B
DATE: Backtracking-Subset sum problem

AIM:

ALGORITHM:

PROGRAM:

def subset_sum(arr, n, sum, memo):


if sum == 0:
return True
if n == 0 and sum != 0:
return False
if memo[n][sum] != -1:
return memo[n][sum] EX: 8B

if arr[n-1] > sum:


memo[n][sum] = subset_sum(arr, n-1, sum, memo)
else:
memo[n][sum] = subset_sum(arr, n-1, sum, memo) or subset_sum(arr, n-
1, sum-arr[n1], memo)
return memo[n][sum]
def is_subset_sum(arr, n, sum):
memo = [[-1 for _ in range(sum+1)] for _ in range(n+1)]
return subset_sum(arr, n, sum, memo)
arr = [3, 34, 4, 12, 5, 2]
sum = 9
n = len(arr)
if is_subset_sum(arr, n, sum):
print("Found a subset with the given sum")
else:
print("No subset with the given sum")

Output:
Found a subset with given sum
RESULT:
EX: 9 A
DATE: Branch and bound-Assignment problem

AIM:

ALGORITHM:

PROGRAM:
from queue import PriorityQueue

def find_min_cost(cost, N):


# Create the initial state
state = [-1] * N
state_cost = 0
q = PriorityQueue()
q.put((0, state, state_cost))
while not q.empty():
EX: 9A
# Get the state with the minimum cost
(min_cost, state, state_cost) = q.get()
# Find the next unassigned task
i = state.index(-1)
for j in range(N):
if state[j] == -1:
# Create the new state
new_state = state.copy()
new_state[j] = i
new_cost = state_cost + cost[i][j]

if i == N - 1:
return new_cost
q.put((new_cost, new_state, new_cost))
return None
# Example usage
cost = [[9, 2, 7, 8], [6, 4, 3, 7], [5, 8, 1, 8], [7, 6, 9, 4]]
N=4
print(find_min_cost(cost, N))

Output:
16
RESULT:
EX: 9 B
DATE: Branch and bound-Travelling salesman problem

AIM:

ALGORITHM:
PROGRAM: EX: 9B

from queue import PriorityQueue

def tsp(graph, start):


n = len(graph)

# Create the initial state


state = [start]
visited = [False] * n
visited[start] = True
q = PriorityQueue()
q.put((0, state, visited))

while not q.empty():


(min_cost, state, visited) = q.get()
last = state[-1]

if len(state) == n:
return min_cost + graph[last][start]
for i in range(n):
if not visited[i]:
new_visited = visited.copy()
new_visited[i] = True
new_state = state + [i]
new_cost = min_cost + graph[last][i]
q.put((new_cost, new_state, new_visited))
return None
# Example usage
graph = [[0, 10, 15, 20],
[10, 0, 35, 25],
[15, 35, 0, 30],
[20, 25, 30, 0]]

start = 0
print(tsp(graph, start))

Output:
80
RESULT:

You might also like

pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy