Вы находитесь на странице: 1из 19

Artificial intelligence Record

Shraddha Muralidhar/1BM15CS143

B.M.S College of Engineering


Computer Science
Contents

1 8 Puzzle Problem 3
1.1 Theory: . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 3
1.2 Code . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 3
1.3 Output . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 5

2 Iterative Deepening Search 7


2.1 Theory: . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 8
2.2 Code . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 8
2.3 Output . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 8

3 A* search algorithm 9
3.1 Theory: . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 9
3.2 Code . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 9

4 Unification Algorithm 11
4.1 Theory: . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 11
4.2 Code: . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 11

5 Tic Tac Toe 13


5.1 Theory: . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 13
5.2 Code: . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 13
g

1
Chapter 1

8 Puzzle Problem

1.1 Theory:
An 8-puzzle consists of a 3*3 grid with the numbers 1 to 8, and one empty space
which is called the slider. The objective is to arrive at a particular goal state, which
is usually the one demonstrated above, which we will be using for this problem.
The slider can only move adjacently left, right, above and below. There are three
approaches to this, and in each approach we will evaluate the best among each set
of possibilities through a Depth First Search Tree.

• Comparing the score: a score is assigned based on the number of matching


tiles between the current and goal state, and the best state is explored further.
We compare this at each step.

• Heuristic approach: Check the number of spaces each number needs to move
to achieve the goal state, at every stage.

• Combined approach: Here we check the number of spaces that only the num-
bers adjacent to the slider need to move to achieve the goal state. This is the
most efficient approach.

The second method is what we apply in our code.

1.2 Code

a =[1 ,2 ,3 ,4 ,5 ,0 ,7 ,8 ,6]
b=[1 ,2 ,3 ,4 ,5 ,6 ,7 ,8 ,0]
h=[0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0]
p=0# t o s t o r e p o s i t i o n o f 0
lm=0# t o s t o r e t h e value o f t h e l a s t moved b l o c k
def h e u r i s t i c ( ) :

3
4 Chapter 1. 8 Puzzle Problem

global p , h
f o r i i n range ( l e n ( a ) ) :
if a[ i ]!=0:
h[ a [ i ]]=0
f o r j i n range ( l e n ( b ) ) :
if a[ j ]!=0:
i f a[ j ]!=b[ j ] :
f o r k i n range ( l e n ( b ) ) :
i f a [ j ]==b [ k ] :
h [ a [ j ] ] = abs ( i n t ( k /3)− i n t ( j /3) ) +abs ( ( k%3)
−( j %3) )
else :
h[ a [ j ]]=0
else :
p= i
return h
def proc ( i ) :
g l o b a l p , h , lm
np=p
minimum=6
p r i n t("−−−−−Move No . : " , i ,"−−−−−")
c r = i n t ( p/3)
c c =p%3
i f cr !=2:
p r i n t ( "Down= " , a [ p + 3 ] )
i f h [ a [ p+3]] <minimum and h [ a [ p + 3 ] ] ! = 0 and lm ! = a [ p + 3 ] :
minimum=h [ a [ p + 3 ] ]
np=p+3
i f cr !=0:
p r i n t ( " Up= " , a [ p − 3])
i f h [ a [ p − 3]] <minimum and h [ a [ p − 3 ] ] ! = 0 and lm ! = a [ p − 3] :
minimum=h [ a [ p − 3]]
np=p−3
i f cc ! = 2 :
p r i n t ( " Right = " , a [ p + 1 ] )
i f h [ a [ p+1]] <minimum and h [ a [ p + 1 ] ] ! = 0 and lm ! = a [ p + 1 ] :
minimum=h [ a [ p + 1 ] ]
np=p+1
i f cc ! = 0 :
p r i n t ( " L e f t = " , a [ p − 1])
i f h [ a [ p − 1]] <minimum and h [ a [ p − 1 ] ] ! = 0 and lm ! = a [ p − 1]:
minimum=h [ a [ p − 1]]
np=p−1
i f minimum==6:
i f h==[0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0]:
p r i n t ( " Solved " )
else :
p r i n t ( " Dead End " )
return 0
else :
a [ p ] , a [ np]= a [ np ] , a [ p ]
1.3. Output 5

lm=a [ p ]
p r i n t ( " Block Moved : " , lm )
p r i n t ( " Current S t a t e : " , a )
h1= h e u r i s t i c ( )
print (" Heuristic : " ,h)
p r i n t ( " P o s i t i o n Of Blank : " , p )
return 1
def main ( ) :
global p
print (" I n i t i a l State : " , a )
h1= h e u r i s t i c ( )
print (" Heuristic : " ,h)
p r i n t ( " P o s i t i o n Of Blank : " , p )
c =1
i =0
while c ! = 0 :
i = i +1
c=proc ( i )
main ( )

1.3 Output

I n i t i a l State : [1 , 2 , 3 , 4 , 5 , 0 , 7 , 8 , 6]
Heuristic : [0 , 0 , 0 , 0 , 0 , 0 , 1 , 0 , 0]
P o s i t i o n Of Blank : 5
−−−−−Move No . : 1 −−−−−
Down= 6
Up= 3
Left= 5
Block Moved : 6
Current S t a t e : [1 , 2 , 3 , 4 , 5 , 6 , 7 , 8 , 0]
Heuristic : [0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0]
P o s i t i o n Of Blank : 8
−−−−−Move No . : 2 −−−−−
Up= 6
Left= 8
Solved
Chapter 2

Iterative Deepening Search

There are two common ways to traverse a graph, BFS and DFS. Considering a Tree
(or Graph) of huge height and width, both BFS and DFS are not very efficient due
to following reasons.

• DFS first traverses nodes going through one adjacent of root, then next adja-
cent. The problem with this approach is, if there is a node close to root, but
not in first few subtrees explored by DFS, then DFS reaches that node very
late. Also, DFS may not find shortest path to a node (in terms of number of
edges).

• BFS goes level by level, but requires more space. The space required by DFS

7
8 Chapter 2. Iterative Deepening Search

is O(d) where d is depth of tree, but space required by BFS is O(n) where n
is number of nodes in tree (Why? Note that the last level of tree can have
around n/2 nodes and second last level n/4 nodes and in BFS we need to
have every level one by one in queue).

2.1 Theory:
IDDFS combines depth-first search’s space-efficiency and breadth-first search’s fast
search (for nodes closer to root).DDFS calls DFS for different depths starting from
an initial value. In every call, DFS is restricted from going beyond given depth. So
basically we do DFS in a BFS fashion.

2.2 Code

// Returns t r u e i f t a r g e t i s r e a c h a b l e from
// s r c within max_depth
bool IDDFS ( s r c , t a r g e t , max_depth )
f o r l i m i t from 0 t o max_depth
i f DLS ( s r c , t a r g e t , l i m i t ) == t r u e
return true
return f a l s e

bool DLS ( s r c , t a r g e t , l i m i t )
i f ( s r c == t a r g e t )
return true ;

// I f reached t h e maximum depth ,


// st op r e c u r s i n g .
i f ( l i m i t <= 0 )
return f a l s e ;

foreach adjacent i of src


i f DLS ( i , t a r g e t , l i m i t ? 1 )
return true

return f a l s e

2.3 Output

True ( T a r g e t i s r e a c h a b l e from s o u r c e within max depth )


Chapter 3

A* search algorithm

A* search is an informed search algorithm used for path-finding and graph traver-
sal. It combines the advantages of both Dijkstra’s algorithm (in that it can find a
shortest path) and Greedy Best-First-Search (in that it can use a heuristic to guide
search). It combines the information that Dijkstra’s algorithm uses (favoring ver-
tices that are close to the starting point) and information that Best-First-Search uses
(favoring vertices that are closer to the goal).

3.1 Theory:
Let g(n) represent the exact cost of the path from the starting point to any vertex n,
and h(n) represent the heuristic estimated cost from vertex n to the goal. Dijkstra’s
algorithms builds a priority queue of nodes ordered on their g(n) values. Best-First-
Search employs a priority queue of nodes ordered on h(n) values. A* balances the
two as it moves from the starting point to the goal. It builds a priority queue of
nodes ordered on f(n) = g(n) + h(n) which is the total estimated path cost through
the node n.

3.2 Code

def A∗−GRAPH−SEARCH ( s t a r t ) :
Let pq be an empty min p r i o r i t y queue
Let c l o s e d be an empty s e t

g( start ) = 0
f ( start ) = h( start )
path ( s t a r t ) = [ ]
pq . push ( s t a r t , f ( s t a r t ) )

while not pq . empty ( ) :

9
10 Chapter 3. A* search algorithm

top = pq . pop ( )
i f i s G o a l ( top ) :
r e t u r n f ( top ) , path ( top )
c l o s e d . add ( top )
f o r e a c h next i n succ ( top ) :
i f next not i n c l o s e d :
g ( next ) = g ( top ) + c o s t ( top , next )
f ( next ) = g ( next ) + h ( next )
path ( next ) = path ( top ) . append ( next )
pq . push ( next , f ( next ) )

Lets work through this example. First, S is expanded and nodes A (f(A)=4) and B
(f(B)=3) are pushed onto the queue. Then, B (having smaller f value) is expanded
and G (f(G)=5) is pushed onto the queue. If we declare victory as soon as we push
it onto the queue, we will choose the path S->B->G (having cost 5) and not the
shorter path S->A->G (having cost 4).
Chapter 4

Unification Algorithm

The unification problem in first-order logic can be expressed as follows: Given two
terms containing some variables, find, if it exists, the simplest substitution (i.e., an
assignment of some term to every variable) which makes the two terms equal. The
resulting substitution is called the most general unifier .

4.1 Theory:
Unification is synonymous with pattern-matching, where you combine together
two structures, where variables in one are allowed to match values in the other.
The simplest form of unification happens whenever you call a function in a
normal language. The caller has arguments, and the callee has parameters. The
parameters are "bound to" the arguments, and that produces an instantiation of
the function.

4.2 Code:
The preceding algorithms assumed that we could find the most general unifier of
two atoms. The problem of unification is the following: given two atoms, deter-
mine if they unify, and, if they do, return an MGU of them.
Procedure Unify ( t1 , t 2 )
Inputs
t1 , t 2 : atoms Output
most g e n e r a l u n i f i e r o f t 1 and t 2 i f i t e x i s t s or 0 o t h e r w i s e
Local
E : a s e t of equality statements
S : substitution
E < −{ t 1 = t 2 }
S={}
while ( E ! = { } )

11
12 Chapter 4. Unification Algorithm

s e l e c t and remove x=y from E


i f ( y i s not i d e n t i c a l t o x ) then
i f ( x i s a v a r i a b l e ) then
r e p l a c e x with y everywhere i n E
and S
S<−{x/y } Union S
e l s e i f ( y i s a v a r i a b l e ) then
r e p l a c e y with x everywhere i n E
and S
S<−{y/x } Union S
e l s e i f ( x i s f ( x1 , . . . , xn ) and y i s f ( y1
, . . . , yn ) ) then
E<−E Union { x1=y1 , . . . , xn=yn }
else
return 0
return S

In the code above ,E is a set of equality statements implying the unification,


and S is a set of equalities of the correct form of a substitution. In this algorithm,
if x/y is in the substitution S, then, by construction, x is a variable that does not
appear elsewhere in S or in E. x and y must have the same predicate and the same
number of arguments; otherwise the unification fails.
Chapter 5

Tic Tac Toe

in the current problem , we need to simulate the two-player game of Tic-Tac-Toe


in the context of a player with the computer such that it always results in the
computer’s victory or a tie.

5.1 Theory:
The program prompts the user about the order of play, following which are a series
of alternate moves on the user’s and computer’s part until a victory is reached or
the board is full. We make a local copy of the board to assess the outcomes of
different moves, and then choose. We employ a number of techniques to decide
the next move in order of priority:

• The winning move, if it is possible in the next turn

• A blocking move, if it’s possible for the player to win in their next turn

• Occupying a randomly selected corner space

• Occupying the centre space

When executed, the game checks for a victory at every move. Otherwise, it termi-
nates when the board has been filled.

5.2 Code:

import random
def drawBoard ( board ) :
# This f u n c t i o n p r i n t s out t h e board t h a t i t was passed .
# " board " i s a l i s t o f 10 s t r i n g s r e p r e s e n t i n g t h e board ( i g n o r e index
0)

13
14 Chapter 5. Tic Tac Toe

print ( ’ | | ’)
p r i n t ( ’ ’ + board [ 7 ] + ’ | ’ + board [ 8 ] + ’ | ’ + board [ 9 ] )
print ( ’ | | ’)
p r i n t(’−−−−−−−−−−−’)
print ( ’ | | ’)
p r i n t ( ’ ’ + board [ 4 ] + ’ | ’ + board [ 5 ] + ’ | ’ + board [ 6 ] )
print ( ’ | | ’)
p r i n t(’−−−−−−−−−−−’)
print ( ’ | | ’)
p r i n t ( ’ ’ + board [ 1 ] + ’ | ’ + board [ 2 ] + ’ | ’ + board [ 3 ] )
print ( ’ | | ’)

def i n p u t P l a y e r L e t t e r ( ) :
# L e t s t h e p l a y e r type which l e t t e r they want t o be .
# Returns a l i s t with t h e player ’ s l e t t e r as t h e f i r s t item , and t h e
computer ’ s l e t t e r as t h e second .
letter = ’ ’
while not ( l e t t e r == ’X ’ or l e t t e r == ’O’ ) :
p r i n t ( ’ Do you want t o be X or O? ’ )
l e t t e r = input ( ) . upper ( )

# t h e f i r s t element i n t h e t u p l e i s t h e player ’ s l e t t e r , t h e second i s


t h e computer ’ s l e t t e r .
i f l e t t e r == ’X ’ :
r e t u r n [ ’ X ’ , ’O’ ]
else :
r e t u r n [ ’O’ , ’X ’ ]

def whoGoesFirst ( ) :
# Randomly choose t h e p l a y e r who goes f i r s t .
i f random . r a n d i n t ( 0 , 1 ) == 0 :
r e t u r n ’ computer ’
else :
r e t u r n ’ player ’

def playAgain ( ) :
# This f u n c t i o n r e t u r n s True i f t h e p l a y e r wants t o play again ,
otherwise i t returns False .
p r i n t ( ’ Do you want t o play again ? ( yes or no ) ’ )
r e t u r n input ( ) . lower ( ) . s t a r t s w i t h ( ’ y ’ )

def makeMove ( board , l e t t e r , move ) :


board [ move ] = l e t t e r

def isWinner ( bo , l e ) :
# Given a board and a player ’ s l e t t e r , t h i s f u n c t i o n r e t u r n s True i f
t h a t p l a y e r has won .
# We use bo i n s t e a d o f board and l e i n s t e a d o f l e t t e r so we don ’ t have
t o type as much .
r e t u r n ( ( bo [ 7 ] == l e and bo [ 8 ] == l e and bo [ 9 ] == l e ) or # a c r o s s t h e
top
5.2. Code: 15

( bo [ 4 ] == le and bo [ 5 ] == le and bo [ 6 ] == l e ) or # a c r o s s t h e middle


( bo [ 1 ] == le and bo [ 2 ] == le and bo [ 3 ] == l e ) or # a c r o s s t h e bottom
( bo [ 7 ] == le and bo [ 4 ] == le and bo [ 1 ] == l e ) or # down t h e l e f t s i d e
( bo [ 8 ] == le and bo [ 5 ] == le and bo [ 2 ] == l e ) or # down t h e middle
( bo [ 9 ] == le and bo [ 6 ] == le and bo [ 3 ] == l e ) or # down t h e r i g h t s i d e
( bo [ 7 ] == le and bo [ 5 ] == le and bo [ 3 ] == l e ) or # diagonal
( bo [ 9 ] == le and bo [ 5 ] == le and bo [ 1 ] == le ) ) # diagonal

def getBoardCopy ( board ) :


# Make a d u p l i c a t e o f t h e board l i s t and r e t u r n i t t h e d u p l i c a t e .
dupeBoard = [ ]
f o r i i n board :
dupeBoard . append ( i )
r e t u r n dupeBoard

def i s S p a c e F r e e ( board , move ) :


# Return t r u e i f t h e passed move i s f r e e on t h e passed board .
r e t u r n board [ move ] == ’ ’

def getPlayerMove ( board ) :


# Let t h e p l a y e r type i n h i s move .
move = ’ ’
while move not i n ’ 1 2 3 4 5 6 7 8 9 ’ . s p l i t ( ) or not i s S p a c e F r e e ( board
, i n t ( move ) ) :
p r i n t ( ’ What i s your next move? (1 − 9) ’ )
move = input ( )
r e t u r n i n t ( move )

def chooseRandomMoveFromList ( board , movesList ) :


# Returns a v a l i d move from t h e passed l i s t on t h e passed board .
# Returns None i f t h e r e i s no v a l i d move .
possibleMoves = [ ]
f o r i i n movesList :
i f i s S p a c e F r e e ( board , i ) :
possibleMoves . append ( i )
i f l e n ( possibleMoves ) ! = 0 :
r e t u r n random . c h o i c e ( possibleMoves )
else :
r e t u r n None

def getComputerMove ( board , c om pu te rL et te r ) :


# Given a board and t h e computer ’ s l e t t e r , determine where t o move and
r e t u r n t h a t move .
i f c o m pu te rL et te r == ’X ’ :
p l a y e r L e t t e r = ’O’
else :
p l a y e r L e t t e r = ’X ’
# Here i s our a l g o r i t h m f o r our T i c Tac Toe AI :
# F i r s t , check i f we can win i n t h e next move
f o r i i n range ( 1 , 1 0 ) :
copy = getBoardCopy ( board )
16 Chapter 5. Tic Tac Toe

i f i s S p a c e F r e e ( copy , i ) :
makeMove ( copy , computerLetter , i )
i f isWinner ( copy , com pu te rL et te r ) :
return i
# Check i f t h e p l a y e r could win on h i s next move , and b l o c k them .
f o r i i n range ( 1 , 1 0 ) :
copy = getBoardCopy ( board )
i f i s S p a c e F r e e ( copy , i ) :
makeMove ( copy , p l a y e r L e t t e r , i )
i f isWinner ( copy , p l a y e r L e t t e r ) :
return i
# Try t o t a k e one o f t h e c o r n e r s , i f they a r e f r e e .
move = chooseRandomMoveFromList ( board , [ 1 , 3 , 7 , 9 ] )
i f move ! = None :
r e t u r n move
# Try t o t a k e t h e c e n t e r , i f i t i s f r e e .
i f i s S p a c e F r e e ( board , 5 ) :
return 5
# Move on one o f t h e s i d e s .
r e t u r n chooseRandomMoveFromList ( board , [ 2 , 4 , 6 , 8 ] )

def i s B o a r d F u l l ( board ) :
# Return True i f every space on t h e board has been taken . Otherwise
return False .
f o r i i n range ( 1 , 1 0 ) :
i f i s S p a c e F r e e ( board , i ) :
return False
r e t u r n True

p r i n t ( ’ Welcome t o T i c Tac Toe ! ’ )


while True :
# R e s e t t h e board
theBoard = [ ’ ’ ] ∗ 10
p l a y e r L e t t e r , co mp ute rL et te r = i n p u t P l a y e r L e t t e r ( )
turn = whoGoesFirst ( )
p r i n t ( ’ The ’ + turn + ’ w i l l go f i r s t . ’ )
gameIsPlaying = True
while gameIsPlaying :
i f turn == ’ player ’ :
# Player ’ s turn .
drawBoard ( theBoard )
move = getPlayerMove ( theBoard )
makeMove ( theBoard , p l a y e r L e t t e r , move )
i f isWinner ( theBoard , p l a y e r L e t t e r ) :
drawBoard ( theBoard )
p r i n t ( ’ Hooray ! You have won t h e game ! ’ )
gameIsPlaying = F a l s e
else :
i f i s B o a r d F u l l ( theBoard ) :
drawBoard ( theBoard )
5.2. Code: 17

p r i n t ( ’ The game i s a t i e ! ’ )
break
else :
turn = ’ computer ’
else :
# Computer ’ s turn .
move = getComputerMove ( theBoard , c om pu te rL ett er )
makeMove ( theBoard , computerLetter , move )
i f isWinner ( theBoard , co mpu te rL et te r ) :
drawBoard ( theBoard )
p r i n t ( ’ The computer has beaten you ! You l o s e . ’ )
gameIsPlaying = F a l s e
else :
i f i s B o a r d F u l l ( theBoard ) :
drawBoard ( theBoard )
p r i n t ( ’ The game i s a t i e ! ’ )
break
else :
turn = ’ player ’

i f not playAgain ( ) :
break

Вам также может понравиться