I'm doing a programming exercise to get familiar with Go. I'm currently writing a parser which parses a string into a command with arguments, e.g:
C w h Should create a new canvas of width w and height h.
B x y c Should fill the entire area connected to (x,y) with "colour" c.
Q Should quit the program.
At first I started using hashes to hold the arguments e.g. w
h
. But this is inflexible and as you can see c
is a colour which will be a string, while the other arguments are integers.
I've started like this:
package main
import (
"errors"
"strconv"
"strings"
)
type command struct {
id string
args map[string]int // Won't work because args can be of mixed types
}
func parseCommand(input string) (command, error) {
if input == "" {
return command{}, errors.New("No input")
}
commandParts := strings.Split(input, " ")
switch commandParts[0] {
case "C":
if (len(commandParts)) != 3 {
return command{}, errors.New("C (create) requires 2 arguments")
}
w, err := strconv.Atoi(commandParts[1])
if err != nil {
return command{}, errors.New("width must be an integer")
}
h, err := strconv.Atoi(commandParts[2])
if err != nil {
return command{}, errors.New("height must be an integer")
}
return command{
id: "create",
args: map[string]int{
"w": w,
"h": h,
},
}, nil
case "B":
if (len(commandParts)) != 4 {
return command{}, errors.New("B (Bucket Fill) requires 3 arguments")
}
x, err := strconv.Atoi(commandParts[1])
if err != nil {
return command{}, errors.New("x must be an integer")
}
y, err := strconv.Atoi(commandParts[2])
if err != nil {
return command{}, errors.New("y must be an integer")
}
return command{
id: "bucketFill",
args: map[string]int{
"x": x,
"y": y,
"c": commandParts[3], // This should be a string!
},
}, nil
case "Q":
return command{
id: "quit",
}, nil
default:
return command{}, errors.New("Command not supported")
}
}
My question is how should I go about parsing an input string into a command, if the arguments I want to return are variable and have mixed types? Thanks.
P.S the commands are free typed in and modify a fake canvas in the terminal e.g:
enter command: C 20 4
----------------------
| |
| |
| |
| |
----------------------
// Didn't mention this one but it's a Line if you didn't guess
enter command: L 1 2 6 2
----------------------
| |
|xxxxxx |
| |
| |
----------------------