例
``
猜谜游戏
maxNum := 100
secretNumber := rand.Intn(maxNum)
fmt.Println("秘密数字为", secretNumber)
fmt.Println("请输入你猜的数字")
reader := bufio.NewReader(os.Stdin)
//用这个方法读取进程文件
for {
input, err := reader.ReadString('\n') //读取到换行符停止,并保存给input
if err != nil {
fmt.Println("读取内容出现了错误", err)
return
}
input = strings.TrimSuffix(input, "\n") // !!!!!!!!注意
input = strings.TrimSuffix(input, "\r") //
guess, err2 := strconv.Atoi(input)
if err2 != nil {
fmt.Println("不合法输入,请输入整形数值", err2)
return
}
if guess > secretNumber {
fmt.Println("太大啦,重新输入一下吧")
continue
} else if guess < secretNumber {
fmt.Println("太小啦,重新输入一下吧")
continue
} else {
fmt.Println("猜对啦,答案就是", guess)
break
}
}
由于回车提交 windows平台会在后面加上\r\n Linux平台则是\n,
会在后面加\r\n
需要用这个方法删除
input = strings.TrimSuffix(input, "\n") input = strings.TrimSuffix(input, "\r")
var guess int
maxNum := 100
secretNumber := rand.Intn(maxNum)
fmt.Println("秘密数字为", secretNumber)
fmt.Println("请输入你猜的数字")
for {
_, err := fmt.Scanf("%d\n", &a)
//这里注意一下"%d\n",如果 fmt.Scanf方法读取到\n换行符,会报错
if err != nil {
fmt.Println(err)
return
}
.
.
//下面一样
简化后
命令行词典
该怎么用go语言来发送HTTP请求,调用第三方的API将查询到的单词翻译出来,再用解析json过来呢
首先右击网页空白处,打开检查,然后打开network,清空请求,再点击翻译,找到api请求,右击请求copy as cURL,之后在curlconverter.com/go/ 一键生成代码 copy到Goland中
type DictRequest struct {
TransType string `json:"trans_type"` //翻译语言
Source string `json:"source"` //翻译内容
UserID string `json:"user_id"`
client := &http.Client{}
request := DictRequest{TransType: "en2zh", Source: "good"}
buf, err := json.Marshal(request) //将固定报文修改成自己设置的
if err != nil {
log.Fatal(err)
}
var data = bytes.NewReader(buf) //将之存到data里
req, err := http.NewRequest("POST", "https://api.interpreter.caiyunai.com/v1/translator", data)
//将这个data发送出去
req.Header.Set(..) //一些请求头
.
.
}
在go里面并不推荐把响应体放在map里,去取值的。应该用一个结构体,把返回来的json反序列化到结构体中 oktools.net/json2go 用这个网址可以快速创建结构体.(如果不会对这个返回操作不做更多的精细化操作,可以用嵌套)
resp, err := client.Do(req)
if err != nil {
log.Fatal(err)
}
defer resp.Body.Close() //go语言编程习惯,为避免资源泄露,用defer关闭流
bodyText, err := io.ReadAll(resp.Body) //拿到返回的json
if err != nil {
log.Fatal(err)
}
var dictResponse DictResponse
err = json.Unmarshal(bodyText, &dictResponse) // 反序列化到结构体中
if err != nil {
log.Fatal(err)
}
fmt.Printf("%#v\n", dictResponse)
现在还不能灵活的翻译,所以可以将这些代码放入写进一个函数通过传入单词参数,来实现翻译功能
if resp.StatusCode != 200 {
log.Fatal("bad StatusCode:", resp.StatusCode, "body", string(bodyText))
} //防止报错
fmt.Println(word, "UK:", dictResponse.Dictionary.Prons.En, "US:", dictResponse.Dictionary.Prons.EnUs)
for _, item := range dictResponse.Dictionary.Explanations {
fmt.Println(item) //将结构体中需要显示的值更改清晰的打印出来
}
log.Fatal()会立即终止程序并输出错误信息
panic()会产生一个异常并让程序崩溃,但是可以在调用的地方进行处理。
将上面合起来放入一个函数中去
func query(word string) {}
SOCKS5代理服务器
在防火墙里开了个口子,让授权的用户通过单个端口可以访问左右的资源。
写爬虫时,防止IP访问频率超过限制报错,可用代理ip池(其中很多代理协议就是socks5协议)解决
原理图
tcp echo server
源代码hi-hi.cn/go
func main() {
server, err := net.Listen("tcp", "127.0.0.1:1080") //侦听端口,返回server
if err != nil {
panic(err)
}
for {
client, err := server.Accept()
//在死循环中不断接受请求,成功就返回一个连接
if err != nil {
log.Printf("Accept failed %v", err)
continue
}
go process(client) //使用go routine 处理连接(可轻松处理上万并发)
//前面要加go关键字相当于子线程
}
}
func process(conn net.Conn) {//用process处理链接
defer conn.Close() //一旦这个process函数结束就关闭连接
reader := bufio.NewReader(conn)//缓冲流,减少底层系统调用
for {
b, err := reader.ReadByte() //每次读一个字节
if err != nil {
break
}
_, err = conn.Write([]byte{b}) //把读入的进行写也即返回(一个字节一个字节读,底层可能合并成几次大的读取操作)
if err != nil {
break
}
}
}
为了方便测试,这里输入什么,服务器就会返回什么,类似为子进程(但开销小)