运行:
pkg main 中的
main方法为执行入口
var 命名变量以及类型
:=可以快速赋值
关键代码:
// Fetchall fetches URLs in parallel and reports their times and sizes.
package main
import (
"fmt"
"io"
"io/ioutil"
"net/http"
"os"
"time"
)
func main() {
start := time.Now()
ch := make(chan string)
for _, url := range os.Args[1:] {
go fetch(url, ch) // start a goroutine
}
for range os.Args[1:] {
fmt.Println(<-ch) // receive from channel ch
}
fmt.Printf("%.2fs elapsed\n", time.Since(start).Seconds())
}
func fetch(url string, ch chan<- string) {
start := time.Now()
resp, err := http.Get(url)
if err != nil {
ch <- fmt.Sprint(err) // send to channel ch
return
}
nbytes, err := io.Copy(ioutil.Discard, resp.Body)
resp.Body.Close() // don't leak resources
if err != nil {
ch <- fmt.Sprintf("while reading %s: %v", url, err)
return
}
secs := time.Since(start).Seconds()
ch <- fmt.Sprintf("%.2fs %7d %s", secs, nbytes, url)
}
使用了 routine以及channel的性质
新建 ch := make(chan string)表示新建一个内部为string的channel
go func() 表示分配一个func任务到一个routine中并发执行
ch <-- fmt.Sprint() 将打印出的内容输出到channel中
<-- ch 表示将channel内容输出到目的地,代码中为println
每一个routine 往 channel send 或者 receive时,会阻塞在调用处,等待另一个routine send or receive
控制流:
if else
switch
命名类型:
指针:存储了变量的内存地址的数据类型,&返回内存地址,*返回指针指向的变量内容;无指针运算
func API
package:标准库之类的
go指针:
主要有两个核心概念
1 切片,指向起始元素的指针+目前元素数量+容量组成
2 类型指针,允许对这个指针类型的数据进行修改,传递数据可以直接使用指针,无须copy数据;不进行偏移或者运算
T = $ variable 表示变量variable的内存地址为T(字符串"x00210"类似的地址字符串)
*T 表示其指向的变量 ( T字符串包含的地址指向的就是variable)
*就是指针
*操作符作为右值时,意义是取指针的值,作为左值时,也就是放在赋值操作符的左边时,表示 a 指针指向的变量