ch6: fix code format

pull/1/head
chai2010 2016-01-21 10:08:07 +08:00
parent 20a8cf71b9
commit 2420954025
7 changed files with 90 additions and 88 deletions

View File

@ -4,8 +4,8 @@
下面來寫我們第一個方法的例子這個例子在package geometry下
<u><i>gopl.io/ch6/geometry</i></u>
```go
gopl.io/ch6/geometry
package geometry
import "math"
@ -14,15 +14,13 @@ type Point struct{ X, Y float64 }
// traditional function
func Distance(p, q Point) float64 {
return math.Hypot(q.X-p.X, q.Y-p.Y)
return math.Hypot(q.X-p.X, q.Y-p.Y)
}
// same thing, but as a method of the Point type
func (p Point) Distance(q Point) float64 {
return math.Hypot(q.X-p.X, q.Y-p.Y)
return math.Hypot(q.X-p.X, q.Y-p.Y)
}
```
上面的代碼里那個附加的參數p叫做方法的接收器(receiver),早期的面向對象語言留下的遺産將調用一個方法稱爲“向一個對象發送消息”。

View File

@ -6,15 +6,15 @@
// An IntList is a linked list of integers.
// A nil *IntList represents the empty list.
type IntList struct {
Value int
Tail *IntList
Value int
Tail *IntList
}
// Sum returns the sum of the list elements.
func (list *IntList) Sum() int {
if list == nil {
return 0
}
return list.Value + list.Tail.Sum()
if list == nil {
return 0
}
return list.Value + list.Tail.Sum()
}
```
@ -22,8 +22,8 @@ func (list *IntList) Sum() int {
下面是net/url包里Values類型定義的一部分。
<u><i>net/url</i></u>
```go
net/url
package url
// Values maps a string key to a list of values.
@ -31,22 +31,22 @@ type Values map[string][]string
// Get returns the first value associated with the given key,
// or "" if there are none.
func (v Values) Get(key string) string {
if vs := v[key]; len(vs) > 0 {
return vs[0]
}
return ""
if vs := v[key]; len(vs) > 0 {
return vs[0]
}
return ""
}
// Add adds the value to key.
// It appends to any existing values associated with key.
func (v Values) Add(key, value string) {
v[key] = append(v[key], value)
v[key] = append(v[key], value)
}
```
這個定義向外部暴露了一個map的類型的變量併且提供了一些能夠簡單操作這個map的方法。這個map的value字段是一個string的slice所以這個Values是一個多維map。客戶端使用這個變量的時候可以使用map固有的一些操作(make切片m[key]等等),也可以使用這里提供的操作方法,或者兩者併用,都是可以的:
<u><i>gopl.io/ch6/urlvalues</i></u>
```go
gopl.io/ch6/urlvalues
m := url.Values{"lang": {"en"}} // direct construction
m.Add("item", "1")
m.Add("item", "2")

View File

@ -4,8 +4,8 @@
```go
func (p *Point) ScaleBy(factor float64) {
p.X *= factor
p.Y *= factor
p.X *= factor
p.Y *= factor
}
```
@ -27,6 +27,7 @@ r := &Point{1, 2}
r.ScaleBy(2)
fmt.Println(*r) // "{2, 4}"
```
或者這樣:
```go

View File

@ -2,13 +2,15 @@
來看看ColoredPoint這個類型
<u><i>gopl.io/ch6/coloredpoint</i></u>
```go
gopl.io/ch6/coloredpoint
import "image/color"
type Point struct{ X, Y float64 }
type ColoredPoint struct {
Point
Color color.RGBA
Point
Color color.RGBA
}
```
@ -47,11 +49,11 @@ p.Distance(q) // compile error: cannot use q (ColoredPoint) as Point
```go
func (p ColoredPoint) Distance(q Point) float64 {
return p.Point.Distance(q)
return p.Point.Distance(q)
}
func (p *ColoredPoint) ScaleBy(factor float64) {
p.Point.ScaleBy(factor)
p.Point.ScaleBy(factor)
}
```
@ -61,8 +63,8 @@ func (p *ColoredPoint) ScaleBy(factor float64) {
```go
type ColoredPoint struct {
*Point
Color color.RGBA
*Point
Color color.RGBA
}
p := ColoredPoint{&Point{1, 1}, red}
@ -77,10 +79,11 @@ fmt.Println(*p.Point, *q.Point) // "{2 2} {2 2}"
```go
type ColoredPoint struct {
Point
color.RGBA
Point
color.RGBA
}
```
然後這種類型的值便會擁有Point和RGBA類型的所有方法以及直接定義在ColoredPoint中的方法。當編譯器解析一個選擇器到方法時比如p.ScaleBy它會首先去找直接定義在這個類型里的ScaleBy方法然後找被ColoredPoint的內嵌字段們引入的方法然後去找Point和RGBA的內嵌字段引入的方法然後一直遞歸向下找。如果選擇器有二義性的話編譯器會報錯比如你在同一級里有兩個同名的方法。
方法隻能在命名類型(像Point)或者指向類型的指針上定義但是多虧了內嵌有些時候我們給匿名struct類型來定義方法也有了手段。
@ -89,15 +92,15 @@ type ColoredPoint struct {
```go
var (
mu sync.Mutex // guards mapping
mapping = make(map[string]string)
mu sync.Mutex // guards mapping
mapping = make(map[string]string)
)
func Lookup(key string) string {
mu.Lock()
v := mapping[key]
mu.Unlock()
return v
mu.Lock()
v := mapping[key]
mu.Unlock()
return v
}
```
@ -105,18 +108,18 @@ func Lookup(key string) string {
```go
var cache = struct {
sync.Mutex
mapping map[string]string
sync.Mutex
mapping map[string]string
}{
mapping: make(map[string]string),
mapping: make(map[string]string),
}
func Lookup(key string) string {
cache.Lock()
v := cache.mapping[key]
cache.Unlock()
return v
cache.Lock()
v := cache.mapping[key]
cache.Unlock()
return v
}
```

View File

@ -68,15 +68,15 @@ func (p Point) Sub(q Point) Point { return Point{p.X - q.X, p.Y - q.Y} }
type Path []Point
func (path Path) TranslateBy(offset Point, add bool) {
var op func(p, q Point) Point
if add {
op = Point.Add
} else {
op = Point.Sub
}
for i := range path {
// Call either path[i].Add(offset) or path[i].Sub(offset).
path[i] = op(path[i], offset)
}
var op func(p, q Point) Point
if add {
op = Point.Add
} else {
op = Point.Sub
}
for i := range path {
// Call either path[i].Add(offset) or path[i].Sub(offset).
path[i] = op(path[i], offset)
}
}
```

View File

@ -4,38 +4,38 @@ Go語言里的集合一般會用map[T]bool這種形式來表示T代表元素
一個bit數組通常會用一個無符號數或者稱之爲“字”的slice或者來表示每一個元素的每一位都表示集合里的一個值。當集合的第i位被設置時我們才説這個集合包含元素i。下面的這個程序展示了一個簡單的bit數組類型併且實現了三個函數來對這個bit數組來進行操作
<u><i>gopl.io/ch6/intset</i></u>
```go
gopl.io/ch6/intset
// An IntSet is a set of small non-negative integers.
// Its zero value represents the empty set.
type IntSet struct {
words []uint64
words []uint64
}
// Has reports whether the set contains the non-negative value x.
func (s *IntSet) Has(x int) bool {
word, bit := x/64, uint(x%64)
return word < len(s.words) && s.words[word]&(1<<bit) != 0
word, bit := x/64, uint(x%64)
return word < len(s.words) && s.words[word]&(1<<bit) != 0
}
// Add adds the non-negative value x to the set.
func (s *IntSet) Add(x int) {
word, bit := x/64, uint(x%64)
for word >= len(s.words) {
s.words = append(s.words, 0)
}
s.words[word] |= 1 << bit
word, bit := x/64, uint(x%64)
for word >= len(s.words) {
s.words = append(s.words, 0)
}
s.words[word] |= 1 << bit
}
// UnionWith sets s to the union of s and t.
func (s *IntSet) UnionWith(t *IntSet) {
for i, tword := range t.words {
if i < len(s.words) {
s.words[i] |= tword
} else {
s.words = append(s.words, tword)
}
}
for i, tword := range t.words {
if i < len(s.words) {
s.words[i] |= tword
} else {
s.words = append(s.words, tword)
}
}
}
```
@ -46,23 +46,23 @@ func (s *IntSet) UnionWith(t *IntSet) {
```go
// String returns the set as a string of the form "{1 2 3}".
func (s *IntSet) String() string {
var buf bytes.Buffer
buf.WriteByte('{')
for i, word := range s.words {
if word == 0 {
continue
}
for j := 0; j < 64; j++ {
if word&(1<<uint(j)) != 0 {
if buf.Len() > len("{") {
buf.WriteByte('}')
}
fmt.Fprintf(&buf, "%d", 64*i+j)"}")}}
}
}
}
buf.WriteByte('}')
return buf.String()
var buf bytes.Buffer
buf.WriteByte('{')
for i, word := range s.words {
if word == 0 {
continue
}
for j := 0; j < 64; j++ {
if word&(1<<uint(j)) != 0 {
if buf.Len() > len("{") {
buf.WriteByte('}')
}
fmt.Fprintf(&buf, "%d", 64*i+j)"}")}}
}
}
}
buf.WriteByte('}')
return buf.String()
}
```

View File

@ -63,9 +63,9 @@ func (c *Counter) Reset() { c.n = 0 }
```go
package log
type Logger struct {
flags int
prefix string
// ...
flags int
prefix string
// ...
}
func (l *Logger) Flags() int
func (l *Logger) SetFlags(flag int)