How to resolve the algorithm Knight's tour step by step in the Tcl programming language

Published on 12 May 2024 09:40 PM

How to resolve the algorithm Knight's tour step by step in the Tcl programming language

Table of Contents

Problem Statement

Problem: you have a standard 8x8 chessboard, empty but for a single knight on some square. Your task is to emit a series of legal knight moves that result in the knight visiting every square on the chessboard exactly once. Note that it is not a requirement that the tour be "closed"; that is, the knight need not end within a single move of its start position. Input and output may be textual or graphical, according to the conventions of the programming environment. If textual, squares should be indicated in algebraic notation. The output should indicate the order in which the knight visits the squares, starting with the initial position. The form of the output may be a diagram of the board with the squares numbered according to visitation sequence, or a textual list of algebraic coordinates in order, or even an actual animation of the knight moving around the chessboard. Input: starting square Output: move sequence

Let's start with the solution:

Step by Step solution about How to resolve the algorithm Knight's tour step by step in the Tcl programming language

Source code in the tcl programming language

package require Tcl 8.6;    # For object support, which makes coding simpler

oo::class create KnightsTour {
    variable width height visited

    constructor {{w 8} {h 8}} {
	set width $w
	set height $h
	set visited {}
    }

    method ValidMoves {square} {
	lassign $square c r
	set moves {}
	foreach {dx dy} {-1 -2  -2 -1  -2 1  -1 2  1 2  2 1  2 -1  1 -2} {
	    set col [expr {($c % $width) + $dx}]
	    set row [expr {($r % $height) + $dy}]
	    if {$row >= 0 && $row < $height && $col >=0 && $col < $width} {
		lappend moves [list $col $row]
	    }
	}
	return $moves
    }

    method CheckSquare {square} {
	set moves 0
	foreach site [my ValidMoves $square] {
	    if {$site ni $visited} {
		incr moves
	    }
	}
	return $moves
    }

    method Next {square} {
	set minimum 9
	set nextSquare {-1 -1}
	foreach site [my ValidMoves $square] {
	    if {$site ni $visited} {
		set count [my CheckSquare $site]
		if {$count < $minimum} {
		    set minimum $count
		    set nextSquare $site
		} elseif {$count == $minimum} {
		    set nextSquare [my Edgemost $nextSquare $site]
		}
	    }
	}
	return $nextSquare
    }

    method Edgemost {a b} {
	lassign $a ca ra
	lassign $b cb rb
	# Calculate distances to edge
	set da [expr {min($ca, $width - 1 - $ca, $ra, $height - 1 - $ra)}]
	set db [expr {min($cb, $width - 1 - $cb, $rb, $height - 1 - $rb)}]
	if {$da < $db} {return $a} else {return $b}
    }

    method FormatSquare {square} {
	lassign $square c r
	format %c%d [expr {97 + $c}] [expr {1 + $r}]
    }

    method constructFrom {initial} {
	while 1 {
	    set visited [list $initial]
	    set square $initial
	    while 1 {
		set square [my Next $square]
		if {$square eq {-1 -1}} {
		    break
		}
		lappend visited $square
	    }
	    if {[llength $visited] == $height*$width} {
		return
	    }
	    puts stderr "rejecting path of length [llength $visited]..."
	}
    }

    method constructRandom {} {
	my constructFrom [list \
		[expr {int(rand()*$width)}] [expr {int(rand()*$height)}]]
    }

    method print {} {
	set s "      "
	foreach square $visited {
	    puts -nonewline "$s[my FormatSquare $square]"
	    if {[incr i]%12} {
		set s " -> "
	    } else {
		set s "\n   -> "
	    }
	}
	puts ""
    }

    method isClosed {} {
	set a [lindex $visited 0]
	set b [lindex $visited end]
	expr {$a in [my ValidMoves $b]}
    }
}


set kt [KnightsTour new]
$kt constructRandom
$kt print
if {[$kt isClosed]} {
    puts "This is a closed tour"
} else {
    puts "This is an open tour"
}


set kt [KnightsTour new 7 7]
$kt constructFrom {0 0}
$kt print
if {[$kt isClosed]} {
    puts "This is a closed tour"
} else {
    puts "This is an open tour"
}


  

You may also check:How to resolve the algorithm Terminal control/Cursor movement step by step in the ZX Spectrum Basic programming language
You may also check:How to resolve the algorithm Monads/Writer monad step by step in the Jsish programming language
You may also check:How to resolve the algorithm CSV data manipulation step by step in the Q programming language
You may also check:How to resolve the algorithm Man or boy test step by step in the Nim programming language
You may also check:How to resolve the algorithm Arrays step by step in the D programming language