0% found this document useful (0 votes)
15 views

Ai Practical-2

Accenture pyq

Uploaded by

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

Ai Practical-2

Accenture pyq

Uploaded by

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

A

Avijit Mohan 08617704423(MCA 3B)

AI/ML LAB PRACTICALS


Q1. Write a program to implement Breadth first search and Depth first search.
Sol.
CODE
from collections import deque

class Graph:
def init (self):
# Dictionary to store the graph as an adjacency list
self.graph = {}

def add_edge(self, node, neighbor):


# Add edge from node to neighbor
if node not in self.graph:
self.graph[node] = []
self.graph[node].append(neighbor)

def bfs(self, start_node):


# Breadth-First Search (BFS) algorithm
visited = set()
queue = deque([start_node])
bfs_order = []

while queue:
node = queue.popleft() # Dequeue a node from the front
if node not in visited:
visited.add(node)
bfs_order.append(node)

# Add all unvisited neighbors to the queue


for neighbor in self.graph.get(node, []):
A
Avijit Mohan 08617704423(MCA 3B)

if neighbor not in visited:


queue.append(neighbor)

return bfs_order

def dfs(self, start_node):


# Depth-First Search (DFS) algorithm (iterative)
visited = set()
stack = [start_node]
dfs_order = []

while stack:
node = stack.pop() # Pop a node from the stack
if node not in visited:
visited.add(node)
dfs_order.append(node)

# Add all unvisited neighbors to the stack


for neighbor in reversed(self.graph.get(node, [])): # Reverse for correct DFS order
if neighbor not in visited:
stack.append(neighbor)

return dfs_order

# Example usage
if name == " main ":
g = Graph()

# Add edges to the graph


g.add_edge(0, 1)
A
Avijit Mohan 08617704423(MCA 3B)

g.add_edge(0, 2)
g.add_edge(1, 2)
g.add_edge(2, 0)
g.add_edge(2, 3)
g.add_edge(3, 3)

# Perform BFS and DFS


print("BFS starting from node 2:", g.bfs(2))
print("DFS starting from node 2:", g.dfs(2))
OUTPUT
A
Avijit Mohan 08617704423(MCA 3B)

Q2. Write a program to implement Best first search and A* algorithm.


Sol.
Best first search
CODE
import heapq

class Graph:
def init (self):
# Dictionary to store the graph as an adjacency list
self.graph = {}

def add_edge(self, node, neighbor, cost):


# Add edge with a cost from node to neighbor
if node not in self.graph:
self.graph[node] = []
self.graph[node].append((neighbor, cost))

def best_first_search(self, start_node, target_node):


# Best First Search algorithm using a priority queue (min-heap)
visited = set()
priority_queue = []
heapq.heappush(priority_queue, (0, start_node)) # (heuristic cost, node)

bfs_order = []

while priority_queue:
cost, node = heapq.heappop(priority_queue)

if node not in visited:


visited.add(node)
A
Avijit Mohan 08617704423(MCA 3B)

bfs_order.append(node)

# If target node is found, return the path


if node == target_node:
return bfs_order

# Explore all neighbors


for neighbor, edge_cost in self.graph.get(node, []):
if neighbor not in visited:
heapq.heappush(priority_queue, (edge_cost, neighbor))

return bfs_order

# Example usage
if name == " main ":
g = Graph()

# Add edges to the graph (node, neighbor, cost)


g.add_edge(0, 1, 1)
g.add_edge(0, 2, 4)
g.add_edge(1, 2, 2)
g.add_edge(1, 3, 5)
g.add_edge(2, 3, 1)

# Perform Best First Search from node 0 to node 3


print("Best First Search Path:", g.best_first_search(0, 3))
OUTPUT
A
Avijit Mohan 08617704423(MCA 3B)

A* Algorithm
CODE
import heapq

class Graph:
def init (self):
# Dictionary to store the graph as an adjacency list
self.graph = {}

def add_edge(self, node, neighbor, cost):


# Add edge with a cost from node to neighbor
if node not in self.graph:
self.graph[node] = []
self.graph[node].append((neighbor, cost))

def heuristic(self, node, target_node):


# Example heuristic: using a dummy heuristic (0 for all nodes)
# You can modify this based on the specific problem, e.g., Euclidean distance,
Manhattan distance, etc.
return 0 # Replace this with an appropriate heuristic for your problem

def a_star(self, start_node, target_node):


# A* Search Algorithm
priority_queue = []
heapq.heappush(priority_queue, (0, start_node)) # (f(n), node)

came_from = {} # To store the path


g_score = {start_node: 0} # Stores the cost from start to each node
f_score = {start_node: self.heuristic(start_node, target_node)} # f(n) = g(n) + h(n)

came_from[start_node] = None
A
Avijit Mohan 08617704423(MCA 3B)

while priority_queue:
current_f_score, current_node = heapq.heappop(priority_queue)

if current_node == target_node:
return self.reconstruct_path(came_from, current_node)

for neighbor, cost in self.graph.get(current_node, []):


tentative_g_score = g_score[current_node] + cost

if neighbor not in g_score or tentative_g_score < g_score[neighbor]:


# Update the path and scores
came_from[neighbor] = current_node
g_score[neighbor] = tentative_g_score
f_score[neighbor] = tentative_g_score + self.heuristic(neighbor, target_node)
heapq.heappush(priority_queue, (f_score[neighbor], neighbor))

return None # If no path is found

def reconstruct_path(self, came_from, current_node):


# Reconstruct the path from the start to the target node
path = []
while current_node is not None:
path.append(current_node)
current_node = came_from[current_node]
path.reverse() # Reverse the path to get it from start to goal
return path

# Example usage
if name == " main ":
A
Avijit Mohan 08617704423(MCA 3B)

g = Graph()

# Add edges to the graph (node, neighbor, cost)


g.add_edge(0, 1, 1)
g.add_edge(0, 2, 4)
g.add_edge(1, 2, 2)
g.add_edge(1, 3, 5)
g.add_edge(2, 3, 1)

# Perform A* search from node 0 to node 3


path = g.a_star(0, 3)
if path:
print("A* Path:", path)
else:
print("No path found")
OUTPUT
A
Avijit Mohan 08617704423(MCA 3B)

Q3. Write a program to implement water jug problem.


Sol.
CODE
from collections import deque

# Function to check if the goal is achievable


def is_solvable(x, y, z):
if z > max(x, y):
return False
return z % gcd(x, y) == 0

# Function to find the Greatest Common Divisor


def gcd(a, b):
while b:
a, b = b, a % b
return a

# BFS function to solve the water jug problem


def water_jug_bfs(x, y, z):
# Initialize the queue for BFS
queue = deque()
queue.append((0, 0)) # Starting state with both jugs empty

visited = set()
visited.add((0, 0))

# To store the sequence of steps


path = []

while queue:
A
Avijit Mohan 08617704423(MCA 3B)

a, b = queue.popleft()
path.append((a, b))

# If we reach the solution (either jug contains exactly z liters)


if a == z or b == z:
return path

# Explore all possible moves (fill, empty, pour)


possible_moves = [
(x, b), # Fill jug 1
(a, y), # Fill jug 2
(0, b), # Empty jug 1
(a, 0), # Empty jug 2
(a - min(a, y - b), b + min(a, y - b)), # Pour jug 1 into jug 2
(a + min(b, x - a), b - min(b, x - a)) # Pour jug 2 into jug 1
]

for move in possible_moves:


if move not in visited:
visited.add(move)
queue.append(move)

return None # If no solution is found

# Main function to run the water jug problem


if name == " main ":
X = 4 # Capacity of Jug 1
Y = 3 # Capacity of Jug 2
Z = 2 # The target amount of water
A
Avijit Mohan 08617704423(MCA 3B)

# Check if the solution is possible


if not is_solvable(X, Y, Z):
print("No solution possible")
else:
# Solve the water jug problem
result = water_jug_bfs(X, Y, Z)
if result:
print("Steps to achieve the target:")
for step in result:
print(f"Jug 1: {step[0]} liters, Jug 2: {step[1]} liters")
else:
print("No solution found")
OUTPUT
A
Avijit Mohan 08617704423(MCA 3B)

Q4. Write a program to implement 4 – Queen problem.


Sol.
CODE
# Function to check if a queen can be placed at (row, col)
def is_safe(board, row, col, N):
# Check for queens in the same column
for i in range(row):
if board[i][col] == 1:
return False

# Check upper left diagonal


for i, j in zip(range(row, -1, -1), range(col, -1, -1)):
if board[i][j] == 1:
return False

# Check upper right diagonal


for i, j in zip(range(row, -1, -1), range(col, N)):
if board[i][j] == 1:
return False

return True

# Recursive utility function to solve the 4-queen problem


def solve_n_queen(board, row, N):
# Base case: If all queens are placed
if row >= N:
return True

# Consider each column and try to place a queen


for col in range(N):
A
Avijit Mohan 08617704423(MCA 3B)

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


board[row][col] = 1 # Place the queen

# Recur to place the rest of the queens


if solve_n_queen(board, row + 1, N):
return True

# If placing the queen doesn't lead to a solution, backtrack


board[row][col] = 0

# If no column can accommodate a queen, return False


return False

# Function to print the board


def print_board(board, N):
for row in range(N):
print(" ".join(str(board[row][col]) for col in range(N)))
print("\n")

# Main function to solve the 4-queen problem


def solve_4_queen_problem():
N = 4 # Size of the board (4x4)
board = [[0 for _ in range(N)] for _ in range(N)] # Initialize the board

if solve_n_queen(board, 0, N):
print("Solution for 4-Queen problem:")
print_board(board, N)
else:
print("No solution exists")
A
Avijit Mohan 08617704423(MCA 3B)

# Run the program


if name == " main ":
solve_4_queen_problem()
OUTPUT
A
Avijit Mohan 08617704423(MCA 3B)

Q5. Write a program to implement AO* algorithm.


Sol.
CODE
import math

class Graph:
def init (self):
# Dictionary to store graph as an adjacency list
# Each node can have AND/OR branches with cost
self.graph = {}

def add_edge(self, parent, children, is_and_node, cost):


# Add edges to the graph (parent -> children with a specified cost)
self.graph[parent] = {'children': children, 'is_and': is_and_node, 'cost': cost}

def get_heuristic(self, node):


# Heuristic function (you can define this according to your problem)
# For simplicity, we'll return a constant heuristic (usually derived from domain
knowledge)
return 0

def ao_star(self, node, backtrack=False):


open_list = {node} # Nodes that need to be processed
solution_graph = {} # Final solution graph
status = {} # Status of each node (SOLVED or not)

while open_list:
current_node = open_list.pop()
children_info = self.graph.get(current_node)

# Base case: If the node has no children, mark it as solved


A
Avijit Mohan 08617704423(MCA 3B)

if children_info is None:
status[current_node] = "SOLVED"
continue

children = children_info['children']
is_and_node = children_info['is_and']
cost = children_info['cost']

# Evaluate the cost of the current node


min_cost = math.inf
selected_children = []

# If this is an AND node, all children must be solved


if is_and_node:
total_cost = sum(self.get_heuristic(child) for child in children) + cost
if total_cost < min_cost:
min_cost = total_cost
selected_children = children
else: # OR node, select the child with the minimum cost
for child in children:
child_cost = self.get_heuristic(child) + cost
if child_cost < min_cost:
min_cost = child_cost
selected_children = [child]

# If no valid children were found, continue (to avoid NoneType error)


if not selected_children:
continue

# Update the solution graph with the best children


A
Avijit Mohan 08617704423(MCA 3B)

solution_graph[current_node] = selected_children

# Add children to open list for further exploration if they are not solved
for child in selected_children:
if status.get(child) != "SOLVED":
open_list.add(child)

# If all children are solved, mark the current node as solved


if all(status.get(child) == "SOLVED" for child in selected_children):
status[current_node] = "SOLVED"

return solution_graph

# Example usage of the AO* algorithm


if name == " main ":
# Creating a graph for the AO* algorithm
g = Graph()

# Add edges in the form (parent, [children], is_and_node, cost)


# For example, node A has children B and C with a cost, and it is an AND node.
g.add_edge('A', ['B', 'C'], True, 1)
g.add_edge('B', ['D', 'E'], True, 2)
g.add_edge('C', ['F'], False, 3)
g.add_edge('D', [], False, 0) # Terminal node
g.add_edge('E', [], False, 0) # Terminal node
g.add_edge('F', [], False, 0) # Terminal node

# Run AO* algorithm starting from node 'A'


solution = g.ao_star('A')
A
Avijit Mohan 08617704423(MCA 3B)

print("Solution Graph:")
for node in solution:
print(f"{node} -> {solution[node]}")
OUTPUT
A
Avijit Mohan 08617704423(MCA 3B)

Q6. Write a program to implement hill climbing & steepest ascent hill climbing algorithm.
Sol.
Hill climbing
CODE
import random

# Define the function to maximize


def objective_function(x):
return -(x ** 2) + 10 * x + 5

# Define the Hill Climbing algorithm


def hill_climbing(start, step_size, max_iterations):
current_solution = start
current_value = objective_function(current_solution)

for i in range(max_iterations):
# Generate neighboring solutions
neighbor_solution = current_solution + random.uniform(-step_size, step_size)
neighbor_value = objective_function(neighbor_solution)

# If the neighbor is better, move to the neighbor


if neighbor_value > current_value:
current_solution = neighbor_solution
current_value = neighbor_value
print(f"Iteration {i}: Moved to better solution at x = {current_solution}, f(x) =
{current_value}")
else:
print(f"Iteration {i}: No improvement at x = {current_solution}, f(x) =
{current_value}")
# Stop if no improvement
break
A
Avijit Mohan 08617704423(MCA 3B)

return current_solution, current_value

# Example usage of the Hill Climbing algorithm


if name == " main ":
# Starting point for hill climbing
start = random.uniform(-10, 10)

# Parameters for hill climbing


step_size = 0.1
max_iterations = 100

# Run hill climbing


best_solution, best_value = hill_climbing(start, step_size, max_iterations)
print(f"Best solution found: x = {best_solution}, f(x) = {best_value}")
OUTPUT

Steepest ascent hill climbing


CODE
import random

# Define the function to maximize


def objective_function(x):
return -(x ** 2) + 10 * x + 5

# Generate neighboring solutions


def generate_neighbors(solution, step_size, num_neighbors=10):
A
Avijit Mohan 08617704423(MCA 3B)

neighbors = []
for _ in range(num_neighbors):
# Generate a neighbor by making a small step
neighbor = solution + random.uniform(-step_size, step_size)
neighbors.append(neighbor)
return neighbors

# Define the Steepest Ascent Hill Climbing algorithm


def steepest_ascent_hill_climbing(start, step_size, max_iterations):
current_solution = start
current_value = objective_function(current_solution)

for i in range(max_iterations):
# Generate neighbors of the current solution
neighbors = generate_neighbors(current_solution, step_size)

# Evaluate all neighbors and find the best one


best_neighbor = current_solution
best_value = current_value

for neighbor in neighbors:


neighbor_value = objective_function(neighbor)
if neighbor_value > best_value:
best_value = neighbor_value
best_neighbor = neighbor

# If the best neighbor is better than the current solution, move to the best neighbor
if best_value > current_value:
current_solution = best_neighbor
current_value = best_value
A
Avijit Mohan 08617704423(MCA 3B)

print(f"Iteration {i}: Moved to better solution at x = {current_solution}, f(x) =


{current_value}")
else:
# If no better neighbor is found, stop
print(f"Iteration {i}: No better neighbor found, stopping at x = {current_solution},
f(x) = {current_value}")
break

return current_solution, current_value

# Example usage of the Steepest Ascent Hill Climbing algorithm


if name == " main ":
# Starting point for hill climbing
start = random.uniform(-10, 10)

# Parameters for hill climbing


step_size = 0.5
max_iterations = 100

# Run Steepest Ascent Hill Climbing


best_solution, best_value = steepest_ascent_hill_climbing(start, step_size, max_iterations)
print(f"Best solution found: x = {best_solution}, f(x) = {best_value}")
A
Avijit Mohan 08617704423(MCA 3B)

OUTPUT
A
Avijit Mohan 08617704423(MCA 3B)

Q7. Write a program to implement travelling salesman problem.


Sol.
CODE
from itertools import permutations

# Define a function to calculate the total distance of a given tour


def calculate_total_distance(tour, distance_matrix):
total_distance = 0
num_cities = len(tour)

# Sum the distances between consecutive cities in the tour


for i in range(num_cities - 1):
total_distance += distance_matrix[tour[i]][tour[i+1]]

# Add the distance to return to the starting city


total_distance += distance_matrix[tour[-1]][tour[0]]

return total_distance

# Brute Force method to solve TSP


def tsp_brute_force(distance_matrix):
num_cities = len(distance_matrix)
cities = list(range(num_cities)) # Cities are labeled 0, 1, 2, ...

# Generate all possible permutations of cities (except the starting city)


all_possible_tours = permutations(cities)

# Track the shortest tour and its distance


shortest_tour = None
shortest_distance = float('inf')
A
Avijit Mohan 08617704423(MCA 3B)

# Evaluate each possible tour


for tour in all_possible_tours:
current_distance = calculate_total_distance(tour, distance_matrix)

# Update if the current tour is shorter than the best found so far
if current_distance < shortest_distance:
shortest_tour = tour
shortest_distance = current_distance

return shortest_tour, shortest_distance

# Example usage of TSP solver


if name == " main ":
# Example distance matrix for 4 cities (symmetric matrix)
# Each element distance_matrix[i][j] represents the distance between city i and city j
distance_matrix = [
[0, 10, 15, 20],
[10, 0, 35, 25],
[15, 35, 0, 30],
[20, 25, 30, 0]
]

# Solve TSP using brute force


shortest_tour, shortest_distance = tsp_brute_force(distance_matrix)

# Print the result


print("Shortest tour:", shortest_tour)
print("Shortest distance:", shortest_distance)
A
Avijit Mohan 08617704423(MCA 3B)

OUTPUT

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