exercise.tour.go google的go官方教程答案
/* Exercise: Loops and Functions #43 */ package main import ( "fmt" "math" ) func Sqrt(x float64) float64 { z := float64(2.) s := float64(0) for { z = z - (z*z - x)/(2*z) if math.Abs(s-z) < 1e-15 { break } s = z } return s } func main() { fmt.Println(Sqrt(2)) fmt.Println(math.Sqrt(2)) } /******************************************************************************************************/ /* Exercise: Maps #44 */ package main import ( "tour/wc" "strings" ) func WordCount(s string) map[string]int { ss := strings.Fields(s) num := len(ss) ret := make(map[string]int) for i := 0; i < num; i++ { (ret[ss[i]])++ } return ret } func main() { wc.Test(WordCount) } /******************************************************************************************************/ /* Exercise: Slices #45 */ package main import "tour/pic" func Pic(dx, dy int) [][]uint8 { ret := make([][]uint8, dy) for i := 0; i < dy; i++ { ret[i] = make([]uint8, dx) for j := 0; j < dx; j++ { ret[i][j] = uint8(i^j+(i+j)/2) } } return ret } func main() { pic.Show(Pic) } /******************************************************************************************************/ /* Exercise: Fibonacci closure #46 */ package main import "fmt" // fibonacci is a function that returns // a function that returns an int. func fibonacci() func() int { x := 0 y := 1 return func() int { x,y = y,x+y return x } } func main() { f := fibonacci() for i := 0; i < 10; i++ { fmt.Println(f()) } } /******************************************************************************************************/ /* Advanced Exercise: Complex cube roots #47 */ package main import ( "fmt" "math/cmplx" ) func Cbrt(x complex128) complex128 { z := complex128(2) s := complex128(0) for { z = z - (cmplx.Pow(z,3) - x)/(3 * (z * z)) if cmplx.Abs(s-z) < 1e-17 { break } s = z } return z } func main() { fmt.Println(Cbrt(2)) } /******************************************************************************************************/ /* Exercise: Errors #57 */ package main import ( "fmt" ) type ErrNegativeSqrt float64 func (e ErrNegativeSqrt) Error() string { return fmt.Sprintf("cannot Sqrt negativ number: %g", float64(e)) } func Sqrt(f float64) (float64, error) { if f < 0 { return 0, ErrNegativeSqrt(f) } return 0, nil } func main() { fmt.Println(Sqrt(2)) fmt.Println(Sqrt(-2)) } /******************************************************************************************************/ /* Exercise: Images #58 */ package main import ( "image" "tour/pic" "image/color" ) type Image struct{ Width, Height int colr uint8 } func (r *Image) Bounds() image.Rectangle { return image.Rect(0, 0, r.Width, r.Height) } func (r *Image) ColorModel() color.Model { return color.RGBAModel } func (r *Image) At(x, y int) color.Color { return color.RGBA{r.colr+uint8(x), r.colr+uint8(y), 255, 255} } func main() { m := Image{100, 100, 128} pic.ShowImage(&m) } /******************************************************************************************************/ /* Exercise: Rot13 Reader #59: 'You cracked the code!' */ package main import ( "io" "os" "strings" ) type rot13Reader struct { r io.Reader } func (rot *rot13Reader) Read(p []byte) (n int, err error) { n,err = rot.r.Read(p) for i := 0; i < len(p); i++ { if (p[i] >= 'A' && p[i] < 'N') || (p[i] >='a' && p[i] < 'n') { p[i] += 13 } else if (p[i] > 'M' && p[i] <= 'Z') || (p[i] > 'm' && p[i] <= 'z'){ p[i] -= 13 } } return } func main() { s := strings.NewReader( "Lbh penpxrq gur pbqr!") r := rot13Reader{s} io.Copy(os.Stdout, &r) } /******************************************************************************************************/ /* Exercise: Equivalent Binary Trees #67 */ package main import ( "tour/tree" "fmt" ) // Walk walks the tree t sending all values // from the tree to the channel ch. func Walk(t *tree.Tree, ch chan int) { _walk(t, ch) close(ch) } func _walk(t *tree.Tree, ch chan int) { if t != nil { _walk(t.Left, ch) ch <- t.Value _walk(t.Right, ch) } } // Same determines whether the trees // t1 and t2 contain the same values. func Same(t1, t2 *tree.Tree) bool { ch1 := make(chan int) ch2 := make(chan int) go Walk(t1, ch1) go Walk(t2, ch2) for i := range ch1 { if i != <- ch2 { return false } } return true } func main() { //tree.New(2) ch := make(chan int) go Walk(tree.New(1), ch) for v := range ch { fmt.Print(v) } fmt.Println(Same(tree.New(1), tree.New(1))) fmt.Println(Same(tree.New(1), tree.New(2))) } /******************************************************************************************************/ /* Exercise: Web Crawler #69 */ package main import ( "fmt" ) type Fetcher interface { // Fetch returns the body of URL and // a slice of URLs found on that page. Fetch(url string) (body string, urls []string, err error) } var store map[string]bool func Krawl(url string, fetcher Fetcher, Urls chan []string) { body, urls, err := fetcher.Fetch(url) if err != nil { fmt.Println(err) } else { fmt.Printf("found: %s %q\n", url, body) } Urls <- urls } func Crawl(url string, depth int, fetcher Fetcher) { Urls := make(chan []string) go Krawl(url, fetcher, Urls) band := 1 store[url] = true // init for level 0 done for i := 0; i < depth; i++ { for band > 0 { band-- next := <- Urls for _, url := range next { if _, done := store[url] ; !done { store[url] = true band++ go Krawl(url, fetcher, Urls) } } } } return } func main() { store = make(map[string]bool) Crawl("http://golang.org/", 4, fetcher) } // fakeFetcher is Fetcher that returns canned results. type fakeFetcher map[string]*fakeResult type fakeResult struct { body string urls []string } func (f *fakeFetcher) Fetch(url string) (string, []string, error) { if res, ok := (*f)[url]; ok { return res.body, res.urls, nil } return "", nil, fmt.Errorf("not found: %s", url) } // fetcher is a populated fakeFetcher. var fetcher = &fakeFetcher{ "http://golang.org/": &fakeResult{ "The Go Programming Language", []string{ "http://golang.org/pkg/", "http://golang.org/cmd/", }, }, "http://golang.org/pkg/": &fakeResult{ "Packages", []string{ "http://golang.org/", "http://golang.org/cmd/", "http://golang.org/pkg/fmt/", "http://golang.org/pkg/os/", }, }, "http://golang.org/pkg/fmt/": &fakeResult{ "Package fmt", []string{ "http://golang.org/", "http://golang.org/pkg/", }, }, "http://golang.org/pkg/os/": &fakeResult{ "Package os", []string{ "http://golang.org/", "http://golang.org/pkg/", }, }, }