Ai Assign
Ai Assign
ARTIFICIAL INTELLEGENCE
ASSIGNMENT
Submitted by:
SUSHRUTH (1NT17CS194)
TEJAS KRISHNA (1NT17CS197)
VARUN G (1NT17CS202)
1|Page
ACKNOWLEDGEMENT
The satisfaction and euphoria that accompany the successful completion of any
task would be incomplete without the mention of the people who made it
possible, whose constant guidance and encouragement crowned our effort with
success. I express my sincere gratitude to our Principal Dr H. C. Nagaraj, Nitte
Meenakshi Institute of Technology for providing facilities.
I hereby like to thank our guide Shilpa Shree, Assistant Professor, Department of
Computer Science & Engineering on her periodic inspection, time to time evaluation
of the project and help to bring the project to the present form.
2|Page
DECLARATION
I hereby declare that,
(i) This report does not contain text, graphics or tables copied and pasted
from the Internet, unless specifically acknowledged, and the source being
detailed in the report and in the References sections.
(ii) All corrections and suggestions indicated during the internal
presentation have been incorporated in the report.
1 SUSHRUTH
2 TEJAS KRISHNA
3 VARUN G
3|Page
Table of Contents
Sl. No CONTENTS
2.
Breadth First Search
3. Depth First Search
6. A* Search Algorithm
9. Conclusion
4|Page
Introduction to Informed search
The informed search technique utilizes the problem specific knowledge in order
to give a clue to the solution of the problem. This type of search strategy
actually prevents the algorithms from stumbling about the goal and the direction
to the solution. Informed search can be advantageous in terms of the cost where
the optimality is achieved at lower search costs.
Here the most important part of the informed technique is the heuristic function
which facilitates in imparting the additional knowledge of the problem to the
algorithm. As a result, it helps in finding the way to the goal through the various
neighbouring nodes. There are various algorithms based on the informed search
such as heuristic depth-first search, heuristic breadth-first search, A*search,
etcetera. Let’s now understand heuristic depth-first search.
5|Page
Introduction to Uninformed search
The uninformed search is different from informed search in the way that it just
provides the problem definition but no further step to finding the solution to the
problem. The primary objective of uninformed search is to differentiate between
the target and non-target state, and it totally ignores the destination it is heading
towards in the path until it discovers the goal and reports successor. This
strategy is also known as a blind search.
There are various search algorithms under this category such as depth-first
search, uniform cost search, breadth-first search, and so on. Let us now
understand the concept behind the uninformed search with the help of depth-
first search.
6|Page
Depth First Search
Algorithm:
7|Page
Program code:
# Constructor
def __init__(self):
8|Page
# Call the recursive helper function to print
# DFS traversal
self.DFSUtil(v,visited)
# Driver code
# Create a graph given in the above diagram
g = Graph()
g.addEdge(0, 1)
g.addEdge(0, 2)
g.addEdge(1, 2)
g.addEdge(2, 0)
g.addEdge(2, 3)
g.addEdge(3, 3)
9|Page
Output and Analysis:
10 | P a g e
Breadth First Search
Algorithm:
11 | P a g e
Program code:
# Constructor
def __init__(self):
while queue:
# Driver code
13 | P a g e
Output and Analysis:
14 | P a g e
Uniformed Cost Search
Algorithm:
15 | P a g e
Program code:
// graph
vector<vector<int> > graph;
// count
int count = 0;
// mark as visited
visited[p.second] = 1;
}
return answer;
}
17 | P a g e
// main function
int main()
{
// create the graph
graph.resize(7);
// add edge
graph[0].push_back(1);
graph[0].push_back(3);
graph[3].push_back(1);
graph[3].push_back(6);
graph[3].push_back(4);
graph[1].push_back(6);
graph[4].push_back(2);
graph[4].push_back(5);
graph[2].push_back(1);
graph[5].push_back(2);
graph[5].push_back(6);
graph[6].push_back(4);
// goal state
vector<int> goal;
return 0;
}
19 | P a g e
Output and Analysis:
Complexity: O( m ^ (1+floor(l/e)))
where,
m is the maximum number of neighbor a node has
l is the length of the shortest path to the goal state
e is the least cost of an edge
20 | P a g e
Greedy Best First Search
Algorithm:
21 | P a g e
Program code:
import networkx as nx
import Queue as Q
def getPriorityQueue(list):
q = Q.PriorityQueue()
q.put(Ordered_Node(heuristics[node],node))
return q,len(list)
if goal == 1:
return goal
visited[v] = True
final_path.append(v)
if v == dest:
goal = 1
else:
pq_list = []
pq,size = getPriorityQueue(G[v])
for i in range(size):
pq_list.append(pq.get().description)
for i in pq_list:
if goal != 1:
22 | P a g e
#print "current city:", i
if visited[i] == False :
return goal
visited = {}
visited[node] = False
final_path = []
prev = -1
if prev != -1:
curr = var
prev = curr
else:
prev = var
return
23 | P a g e
class Ordered_Node(object):
self.priority = priority
self.description = description
return
def getHeuristics(G):
heuristics = {}
f = open('heuristics.txt')
for i in G.nodes():
node_heuristic_val = f.readline().split()
heuristics[node_heuristic_val[0]] = node_heuristic_val[1]
return heuristics
def CreateGraph():
G = nx.Graph()
f = open('input.txt')
n = int(f.readline())
for i in range(n):
graph_edge_list = f.readline().split()
24 | P a g e
G.add_edge(graph_edge_list[0], graph_edge_list[1], length =
graph_edge_list[2])
pos = nx.spring_layout(G)
val_map = {}
val_map[source] = 'green'
val_map[dest] = 'red'
return pos
#main function
if __name__ == "__main__":
G, source,dest = CreateGraph()
heuristics = getHeuristics(G)
plt.show()
25 | P a g e
Output and Analysis:
The worst case time complexity for Best First Search is O(n * Log n) where n is
number of nodes. In worst case, we may have to visit all nodes before we reach
goal. Note that priority queue is implemented using Min(or Max) Heap, and insert
and remove operations take O(log n) time.
Performance of the algorithm depends on how well the cost or evaluation function
is designed.
26 | P a g e
A* Search
Algorithm:
27 | P a g e
Program code:
import java.util.*;
public T point;
public Double f;
public Double g;
public Path parent;
/**
* Default c'tor.
*/
public Path(){
parent = null;
point = null;
g = f = 0.0;
}
/**
* C'tor by copy another object.
*
* @param p The path object to clone.
*/
public Path(Path p){
this();
parent = p;
g = p.g;
f = p.f;
}
/**
* Compare to another object using the total cost f.
*
* @param o The object to compare to.
* @see Comparable#compareTo()
* @return <code>less than 0</code> This object is smaller
28 | P a g e
* than <code>0</code>;
* <code>0</code> Object are the same.
* <code>bigger than 0</code> This object is bigger
* than o.
*/
public int compareTo(Object o){
Path p = (Path)o;
return (int)(f - p.f);
}
/**
* Get the last point on the path.
*
* @return The last point visited by the path.
*/
public T getPoint(){
return point;
}
/**
* Set the
*/
public void setPoint(T p){
point = p;
}
}
/**
* Check if the current node is a goal for the problem.
*
* @param node The node to check.
* @return <code>true</code> if it is a goal, <code>false</else>
otherwise.
*/
protected abstract boolean isGoal(T node);
/**
* Cost for the operation to go to <code>to</code> from
* <code>from</from>.
*
29 | P a g e
* @param from The node we are leaving.
* @param to The node we are reaching.
* @return The cost of the operation.
*/
protected abstract Double g(T from, T to);
/**
* Estimated cost to reach a goal node.
* An admissible heuristic never gives a cost bigger than the real
* one.
* <code>from</from>.
*
* @param from The node we are leaving.
* @param to The node we are reaching.
* @return The estimated cost to reach an object.
*/
protected abstract Double h(T from, T to);
/**
* Generate the successors for a given node.
*
* @param node The node we want to expand.
* @return A list of possible next steps.
*/
protected abstract List<T> generateSuccessors(T node);
/**
* Check how many times a node was expanded.
*
* @return A counter of how many times a node was expanded.
*/
public int getExpandedCounter(){
return expandedCounter;
}
30 | P a g e
/**
* Default c'tor.
*/
public AStar(){
paths = new PriorityQueue<Path>();
mindists = new HashMap<T, Double>();
expandedCounter = 0;
lastCost = 0.0;
}
/**
* Total cost function to reach the node <code>to</code> from
* <code>from</code>.
*
* The total cost is defined as: f(x) = g(x) + h(x).
* @param from The node we are leaving.
* @param to The node we are reaching.
* @return The total cost.
*/
protected Double f(Path p, T from, T to){
Double g = g(from, to) + ((p.parent != null) ? p.parent.g : 0.0);
Double h = h(from, to);
p.g = g;
p.f = g + h;
return p.f;
}
/**
* Expand a path.
*
* @param path The path to expand.
*/
private void expand(Path path){
T p = path.getPoint();
Double min = mindists.get(path.getPoint());
/*
* If a better path passing for this point already exists then
31 | P a g e
* don't expand it.
*/
if(min == null || min.doubleValue() > path.f.doubleValue())
mindists.put(path.getPoint(), path.f);
else
return;
for(T t : successors){
Path newPath = new Path(path);
newPath.setPoint(t);
f(newPath, path.getPoint(), t);
paths.offer(newPath);
}
expandedCounter++;
}
/**
* Get the cost to reach the last node in the path.
*
* @return The cost for the found path.
*/
public Double getCost(){
return lastCost;
}
/**
* Find the shortest path to a goal starting from
* <code>start</code>.
*
* @param start The initial node.
* @return A list of nodes from the initial point to a goal,
* <code>null</code> if a path doesn't exist.
*/
public List<T> compute(T start){
try{
Path root = new Path();
root.setPoint(start);
32 | P a g e
/* Needed if the initial point has a cost. */
f(root, start, start);
expand(root);
for(;;){
Path p = paths.poll();
if(p == null){
lastCost = Double.MAX_VALUE;
return null;
}
T last = p.getPoint();
lastCost = p.g;
if(isGoal(last)){
LinkedList<T> retPath = new
LinkedList<T>();
for(Path i = p; i != null; i =
i.parent){
retPath.addFirst(i.getPoint());
}
return retPath;
}
expand(p);
}
}
catch(Exception e){
e.printStackTrace();
}
return null;
}
}
33 | P a g e
Output and Analysis:
34 | P a g e
Depth Limited Search
Algorithm:
35 | P a g e
Program code:
36 | P a g e
37 | P a g e
Output and Analysis:
38 | P a g e
Iterative deepening DFS
Algorithm:
return false
39 | P a g e
Program code:
def __init__(self,vertices):
# No. of vertices
self.V = vertices
41 | P a g e
Output and Analysis:
42 | P a g e
Conclusion
43 | P a g e
References
https://www.geeksforgeeks.org
https://www.hackerearth.com
44 | P a g e