- The idea is to iteratively and incrementally develop connected4 game which can be played as human vs human or human vs computer.
- There are solutions available that can ensure computer’s victory.
- Instead of using such solution, this project will use heuristic based approach(vs knowledge base approach) for the computer player.
- Well, because solutions that ensure victory may not provide much advantage(could be a wrong assumption) in designing code to allow changing board representation, heuristic function etc. Even such design can make the computer player slow! Also implementing such solution may require lot of work in optimization which will defeat the goal of learning haskell so :)
- Current tentative milestones[6/7]:
- [X] Implement a simple human vs human text based game.
- [X] Restructure code to allow changing board representation.
- [X] Implement a Binary Board representation.
- [X] Restructure code to allow different players(note: at present human player is considered separately)
- [X] Implement alpha beta algorithm which can be used with two player games and not just connected4 game.
- [X] Implement a good enough computer player - which involves making a good heuristic function.
- [ ] Implement a better text-based version for display with proper menu for user to choose players etc
- Possible Future impovements[0/3]:
- [ ] Implement a graphics based version.
- [ ] At present BitBoard is slower than SimpleBoard - which defeats the purpose of using bits for representing board!
- [ ] Use transposition tables.
You are a TA at a university, and you want to evaluate your student’s homework without executing their (untrusted) code. You decide to write a small web-service that takes bytecode as input, and interprets the results.
The bytecode language you need to support includes basic arithmetic and variables. The bytecode language is stack, rather than register based. ByteCode (right) is given for the following pseudo code (left):
Pseudo Code | ByteCode |
---|---|
function f() { | |
x = 1 | LOAD_VAL 1 |
WRITE_VAR ‘x’ | |
y = 2 | LOAD_VAL 2 |
WRITE_VAR ‘y’ | |
return (x + 1) * y | READ_VAR ‘x’ |
LOAD_VAL 1 | |
ADD | |
READ_VAR ‘y’ | |
MULTIPLY | |
RETURN_VALUE | |
} |
Add a data type `ByteCode` that can represent bytecode like in the example above, along with an interpreter for said bytecode. Make sure your code is total.
>cd haskell-minis
>cabal build bytecode
>cat input/bytecode-example-input.txt | cabal run bytecode
>cd haskell-minis
>cabal repl bytecode
# Some examples
λ> :set -XOverloadedStrings
λ> runByteCode "LOAD_VAL 5\nRETURN_VALUE"
"Success: Return: 5"
λ> runByteCode "LOAD_VAL 5\nLOAD_VAL 10\nADD\nRETURN_VALUE"
"Success: Return: 15"
#There are some inputs defined in the code which will generate *syntax errors*
λ> serror0
"LOAD_VAL4"
λ> runByteCode serror0
"Syntax Error: Either *operator* is invalid or it is followed by extra/invalid characters in line [LOAD_VAL4]"
λ> serror1
"LOAD_VAL 4 \nADD"
λ> runByteCode serror1
"Syntax Error: Either *integer* is invalid or extra spaces in line [LOAD_VAL 4 ]"
λ> serror2
"LOAD_VAL 4\nADD ab"
λ> runByteCode serror2
"Syntax Error: Either *operator* is invalid or it is followed by extra/invalid characters in line [ADD ab]"
#Similarly some inputs which will generate *runtime errors*
λ> perror0
"RETURN_VALUE"
λ> runByteCode perror0
"Error: Stack under flow"
λ> runByteCode perror4
"Error: Division by zero"
#Example given in the problem statement
λ> input1
"LOAD_VAL 1\nWRITE_VAR \226\8364\732x\226\8364\8482\nLOAD_VAL 2\nWRITE_VAR \226\8364\732y\226\8364\8482\nREAD_VAR \226\8364\732x\226\8364\8482\nLOAD_VAL 1\nADD\nREAD_VAR \226\8364\732y\226\8364\8482\nMULTIPLY\nRETURN_VALUE"
λ> runByteCode input1
"Success: Return: 4"