package main
import (
"bufio"
"fmt"
"os"
"unicode"
)
var keywords = map[string]int{
"begin": 1,
"if": 2,
"then": 3,
"while": 4,
"do": 5,
"end": 6,
}
func lexicalAnalysis(input string) { //词法分析程序
var p int = 0
scanner := func() (int, string) {
var syn int
var token string
for p < len(input) && input[p] == ' ' {
p++ //跳过空格
}
if unicode.IsLetter(rune(input[p])) {
for p < len(input) && (unicode.IsLetter(rune(input[p])) || unicode.IsDigit(rune(input[p]))) { //如果当前是字符,那么把它加入到token中
token += string(input[p])
p++
}
_, ok := keywords[token]
if ok {
syn = keywords[token]
} else {
syn = 10
}
} else {
if unicode.IsDigit(rune(input[p])) {
syn = 11
token = string(input[p])
p++
} else {
switch input[p] {
case '+':
token = "+"
syn = 13
p++
case '-':
token = "-"
syn = 14
p++
case '*':
token = "*"
syn = 15
p++
case '/':
token = "/"
syn = 16
p++
case ':':
if p+1 < len(input) && input[p+1] == '=' {
syn = 18
token = ":="
p += 2
} else {
token = ":"
syn = 17
p++
}
case '<':
if p+1 < len(input) && input[p+1] == '>' {
syn = 21
token = "<>"
p += 2
} else if p+1 < len(input) && input[p+1] == '=' {
syn = 22
token = "<="
p += 2
} else {
syn = 20
token = "<"
p++
}
case '>':
if p+1 < len(input) && input[p+1] == '=' {
syn = 24
token = ">="
p += 2
} else {
syn = 23
token = ">"
p++
}
case '=':
syn = 25
token = "="
p++
case ';':
syn = 26
token = ";"
p++
case '(':
syn = 27
token = "("
p++
case ')':
syn = 28
token = ")"
p++
case '#':
syn = 0
token = "#"
p++
default:
syn = -1
token = string(input[p])
p++
}
}
}
return syn, token
}
for p < len(input) {
syn, token := scanner()
if syn == -1 {
fmt.Println("错误:非法字符", token)
break
} else {
res := fmt.Sprintf("(%d,%s)", syn, token)
fmt.Print(res + " ")
}
}
}
func main() {
fmt.Printf("请输入代码段\n")
reader := bufio.NewReader(os.Stdin)
readBytes, _, _ := reader.ReadLine()
var codeSegment string = string(readBytes)
//input := "begin x:=9;if x>0 then x:=2*x+1/3;end#"
lexicalAnalysis(codeSegment)
}