Golang基础上手|青训营笔记

121 阅读4分钟

这是我参与「第三届青训营 -后端场」笔记创作活动的的第1篇笔记

怕什么真理无穷,进一步有进一步的欢喜

GO语言的特性

  • 高性能,高并发
  • 语法简单
  • 标准库异常丰富
  • 工具链很完善
  • 静态链接,快速编译
  • 跨平台,垃圾回收

上手比C++友好很多,但是速度并不慢

Json处理

结构体中的变量如果 首字母是大写意味着是全局变量

Json处理主要是使用json.Marshal()的方法将对象转换成为json格式,json.Unmarshal()将json格式的数据中对应的值写到给的结构体中,注意传递指针

源码:

// JSON cannot represent cyclic data structures and Marshal does not
// handle them. Passing cyclic structures to Marshal will result in
// an error.
//
func Marshal(v interface{}) ([]byte, error) {
  e := newEncodeState()
​
  err := e.marshal(v, encOpts{escapeHTML: true})
  if err != nil {
    return nil, err
  }
  buf := append([]byte(nil), e.Bytes()...)
​
  encodeStatePool.Put(e)
​
  return buf, nil
}

实例:

package main
​
import (
  "encoding/json"
  "fmt"
)
​
type userInfo struct {
  Name  string //变量首字母大写意味着是全局
  Age   int    `json:"age"`
  Hobby []string
}
​
func main() {
  a := userInfo{Name: "Shao", Age: 19, Hobby: []string{"CPP", "Golang"}}
  buf, err := json.Marshal(a)
  if err != nil {
    panic(err)
  }
  fmt.Println(buf)
  fmt.Println(string(buf))
}
​

时间处理

使用time包中对应的方法能够对于时间对象进行处理

  • time.Now:获得当前的时间,包括年月日时分秒
  • time.Unix:获得时间戳
  • xxx.Sub(time1):获得xxx与time1时间的差值
package main
​
import (
  "fmt"
  "time"
)
​
func main() {
  now := time.Now() //当前时间
  fmt.Println(now)
​
  t := time.Date(2022, 3, 27, 1, 25, 36, 0, time.UTC)
  fmt.Println(t)
​
  //获得时间中的时分秒等
  fmt.Println(t.Year(), t.Month(), t.Day(), t.Hour(), t.Minute())
  
  //相差多少的时间
  diff := now.Sub(t)
  fmt.Println(diff.Minutes(), diff.Seconds())
}
​

数字解析

使用xxx.ParseFloat,xxx.ParseInt等方法进行字符串到类型的转换

🌰:n, _:= strconv.ParseInt("111", 10, 64):将111转换成十进制

进程信息

类似于C中处理char **argv

Golang中通过os.Args进行运行时输入参数的处理,参数同c中运行时参数相同

项目:在线词典

usage:filename word

在运行go程序的时候传入需要转换的单词,程序会自动输出单词的各种释意思

运行🌰:

/private/var/folders/t6/xv8v0kcx14jbb47wbhd9654r0000gn/T/GoLand/___go_build_main_go hello
hello UK: [ˈheˈləu] US: [həˈlo]
int.喂;哈罗
n.引人注意的呼声
v.向人呼(喂)

version1

第一步我们就是调用api呀,直接就是 发送请求到翻译的网站,然后我们显示得到的结果

首先创建http:client,调用http.NewRequest(......)将我们配置好的参数传递过去鸭,这里我们将请求报文写死

client := &http.Client{}
  var data = strings.NewReader(`{"trans_type":"en2zh","source":"good"}`)
  req, err := http.NewRequest("POST", "https://api.interpreter.caiyunai.com/v1/dict", data)
  if err != nil {
    log.Fatal(err)
  }
////设置头部字段,很多很多的字段
req.Header.Set()
req.Header.Set()
req.Header.Set()
////

上面我们将http请求发送到对应的翻译网站了,现在进行处理

if err != nil {
    log.Fatal(err)
  }
  defer resp.Body.Close()         //最后的时候将body进行删除
  bodyText, err := ioutil.ReadAll(resp.Body)    //返回的是字节流
  if err != nil {
    log.Fatal(err)
  }
  fmt.Printf("%s\n", bodyText)    //将得到的内容打印出来

version2

我们在创建请求的时候,data是手写string形式的,那么我们这次设置一个struct用于存储json对应的字段

type DictRequest struct {
  TransType string `json:"trans_type"`
  Source    string `json:"source"`
  UserID    string `json:"user_id"`
}

version3

我们上述版本最终打印的都是json格式的 极其复杂的字符串,很懵逼,不容易看并且很多没有用的(因为我只是想看最终的翻译的那些字段),那么怎么解决呢?

我们可以用结构体进行存储嘛,最终翻译的结果以变量的形式得到,也便于进行处理,这里老师推荐了一个网站, 输入json就能够得到对应的结构体oktools.net/json2go

我们创建一个结构体的对象用于接收我们翻译的结果,接收就是用json.Unmarshal()进行处理,之后对结构体对象进行处理就能得到想要的结果了

err = json.Unmarshal(bodyText, &dictResponse)
if err != nil {
   log.Fatal(err)
}
fmt.Printf("%#v\n", dictResponse)

version4

version3进行封装一下,data中的查询的单词不是写死的,作为变量传入进去,然后对于解析到的json对象中字段进行过滤一下(我不太明白),然后打印就好了

Proxy

version1

第一个版本就是简单的echo,我自己在C中同样也是实现过,就是server监听,client进行连接,将客户端发送的数据原样返回

使用nc命令模拟客户端,输入ip + port即可连接server

剩余部分细节太多了,而且我还没怎么看懂😢