Go 语言学习

最近要学习一下分布式文件系统,了解一下分布式文件系统的容错机制,就开启了自学MIT 6.824 Distributed System Spring 2014课程。 

以前在学校里面听过陈康老师讲过几节课,有一些印象,确实很难。本来以为也是C或者C++实现的,万万没想到的是,竟然用高大上的Go语言重写了分布式文件系统的框架,

这让我等小菜只好膜拜,只好开始学习Go语言。(参考资料:http://golang.org/doc/)

  1. 学习记录

http://tour.golang.org/  一个练习教程,过一遍基本上Go编程有了初步的了解。 下一步需要深入研究GOROUTINE的原理以及应用。

1) 变量声明和初始化 ( 变量声明 := ,var,以及struct、Arrays、slice、map、channels、mathod、interface)

var i, j int = 1, 2
var c, python, java = true, false, "no!" 

struct:

type Vertex struct {
X int
Y int
}

Arrays: var a [10]int

Slices: p := []int{2, 3, 5, 7, 11, 13}

a := make([]int,5)

var m map[string]Vertex 

m = make(map[string]Vertex]
var m = map[string]Vertex{
"Bell Labs": Vertex{
40.68433, -74.39967,
},
"Google": Vertex{
37.42202, -122.08408,
},
}

函数的声明  

func swap(x, y string) (string, string)

hypot := func(x, y float64) float64 {
return math.Sqrt(x*x + y*y)
}

Function closures

method 和 interface 自由扩展

type Vertex struct {
X, Y float64
}

func (v *Vertex) Abs() float64 {
return math.Sqrt(v.X*v.X + v.Y*v.Y)
}

Errors

type error interface {

    Error() string

}

Channels

ch := make(chan int)

ch := make(chan int, 100)
Sends to a buffered channel block only when the buffer is full. Receives block when the buffer is empty.
类似于C中的Pipe,用来线程之间传递数据

 

2) 基本语法

 GO中没有while,用for来表示,如for  i < 100 { }

 switch  、 if 、 for 

3) 练习题 

 Exercise: Maps

  1. package main
  2. import (
  3. "code.google.com/p/go-tour/wc"
  4. "strings"
  5. )
  6. func WordCount(s string) map[string]int {
  7. words := strings.Fields(s)
  8. mp := make(map[string]int)
  9. for _,word := range words {
  10. 10. mp[word] += 1
  11. }
  12. return mp
  13. }
  14. func main() {
  15. wc.Test(WordCount)
  16. }

Exercise: Fibonacci closure

  1. func fibonacci() func() int {
  2. a:=0
  3. b:=1
  4. count := 1
  5. res := func() int {
  6. if count==1 {
  7. count++
  8. return 1
  9.  } else {
  10.  c :=a + b
  11.  a = b
  12.  b = c
  13.  return c
  14. }
  15. }
  16. return res
  17. }
  18. func main() {
  19. f := fibonacci()
  20. for i := 0; i < 10; i++ {
  21. fmt.Println(f())
  22. }
  23. }

Advanced Exercise: Complex cube roots

  1. func Cbrt(x complex128) complex128 {
  2. // var z, z1 complex64
  3. z := complex128(1)
  4. z1 := z - ((z*z*z - x) / (3*z*z))
  5. i := 1
  6. for z1!=x && i<10 {
  7. z1 = z1 - ((z1*z1*z1 - x) / (3*z1*z1))
  8. i++;
  9. }
  10. return z1
  11. }
  12. func main() {
  13. fmt.Println(Cbrt(2))
  14. }  (需要把整数强行转换成complex128,另外也可以简单化,直接用real取实数部分)

Exercise: Errors

  1. type ErrNegativeSqrt float64
  2. func (e ErrNegativeSqrt) Error() string {
  3. return fmt.Sprintf("cantnot Sqrt negative number:%v",float64(e))
  4. }
  5. func Sqrt(f float64) (float64, error) {
  6. if f < 0 {
  7. return 0,ErrNegativeSqrt(f); 
  8. }
  9. z := f
  10. for i:=0;i<10;i++ {
  11. z = (z+f/z)/2;
  12. }
  13. return z, nil
  14. }
  15. Exercise: Rot13 Reader
  16. type rot13Reader struct {
  17. r io.Reader
  18. }
  19. func ( rs *rot13Reader) Read(p []byte) (n int, err error) {
  20. n,err = rs.r.Read(p)
  21. for i := 0; i < len(p); i++ {
  22. if (p[i] >= 'A' && p[i] < 'N') || (p[i] >='a' && p[i] < 'n') {
  23. p[i] += 13
  24. } else if (p[i] > 'M' && p[i] <= 'Z') || (p[i] > 'm' && p[i] <= 'z'){
  25. p[i] -= 13
  26. }
  27. }
  28. return 
  29. }
  30. func main() {
  31. s := strings.NewReader(
  32. "Lbh penpxrq gur pbqr!")
  33. r := rot13Reader{s}
  34. io.Copy(os.Stdout, &r)
  35. }

Exercise: Web Crawler

  1. type UrlData struct {
  2. url string
  3. depth int
  4. }
  5. type Fetcher interface {
  6. // Fetch returns the body of URL and
  7. // a slice of URLs found on that page.
  8. Fetch(url string) (body string, urls []string, err error)
  9. }
  10. // Crawl uses fetcher to recursively crawl
  11. // pages starting with url, to a maximum of depth.
  12. func Crawl(url string, depth int, fetcher Fetcher,urldata chan<- *UrlData,quit chan<- int) {
  13. // TODO: Fetch URLs in parallel.
  14. // TODO: Don't fetch the same URL twice.
  15. // This implementation doesn't do either:
  16. defer func() { quit <- 1}()
  17. if depth <= 0 {
  18. return
  19. }
  20. body, urls, err := fetcher.Fetch(url)
  21. if err != nil {
  22. fmt.Println(err)
  23. return
  24. }
  25. fmt.Printf("found: %s %q\n", url, body)
  26. for _, u := range urls {
  27. urldata <- &UrlData{u,depth-1}
  28. }
  29. return
  30. }
  31. func main() {
  32. urldata := make(chan *UrlData)
  33. quit := make(chan int)
  34. url_cache := make(map[string]bool)
  35. // url_cache["http://golang.org/"] = true; 
  36. // go Crawl("http://golang.org/", 4, fetcher,urldata,quit)
  37. go func() { urldata <- &UrlData{"http://golang.org/",4} }() 
  38. Loop:
  39. for i:=0;; {
  40. select {
  41. case <-quit:
  42. i--
  43. if i==0 {
  44. break Loop
  45. }
  46. case url := <- urldata:
  47. if url_cache[url.url] {
  48. break;
  49. }
  50. url_cache[url.url]=true
  51. go Crawl(url.url,url.depth,fetcher,urldata,quit);
  52. i++;
  53. }
  54. }
  55. }

Go语言更加灵活,如声明更加便捷,可以直接用短声明(:=), Switch可以没有condition,另外也可以在case中进行判断;包含了function value,能够对函数更有效处理;另外函数可以同时返回多个值,方便处理;包含了interface,而且struct和任意封装类型都可以扩展方法;除此之外,Go 中包含了function value,Closures,以及很强大的Goroutines,这个太强大了,我了解的不多,还需要后续继续研究。

posted @ 2014-06-25 17:50  purejade  阅读(315)  评论(0编辑  收藏  举报