...
1
2
3 package main
4
5 import (
6 "errors"
7 "fmt"
8 )
9
10 func assert(b bool) {
11 if !b {
12 panic("oops")
13 }
14 }
15
16 type I int
17
18 func (i I) add(x int) int {
19 return int(i) + x
20 }
21
22 func valueReceiver() {
23 var three I = 3
24 assert(three.add(5) == 8)
25 var add3 func(int) int = three.add
26 assert(add3(5) == 8)
27 }
28
29 type S struct{ x int }
30
31 func (s *S) incr() {
32 s.x++
33 }
34
35 func (s *S) get() int {
36 return s.x
37 }
38
39 func pointerReceiver() {
40 ps := new(S)
41 incr := ps.incr
42 get := ps.get
43 assert(get() == 0)
44 incr()
45 incr()
46 incr()
47 assert(get() == 3)
48 }
49
50 func addressibleValuePointerReceiver() {
51 var s S
52 incr := s.incr
53 get := s.get
54 assert(get() == 0)
55 incr()
56 incr()
57 incr()
58 assert(get() == 3)
59 }
60
61 type S2 struct {
62 S
63 }
64
65 func promotedReceiver() {
66 var s2 S2
67 incr := s2.incr
68 get := s2.get
69 assert(get() == 0)
70 incr()
71 incr()
72 incr()
73 assert(get() == 3)
74 }
75
76 func anonStruct() {
77 var s struct{ S }
78 incr := s.incr
79 get := s.get
80 assert(get() == 0)
81 incr()
82 incr()
83 incr()
84 assert(get() == 3)
85 }
86
87 func typeCheck() {
88 var i interface{}
89 i = (*S).incr
90 _ = i.(func(*S))
91
92 var s S
93 i = s.incr
94 _ = i.(func())
95 }
96
97 type errString string
98
99 func (err errString) Error() string {
100 return string(err)
101 }
102
103
104 func regress1(x error) func() string {
105 return x.Error
106 }
107
108
109
110 func nilInterfaceMethodValue() {
111 err := errors.New("ok")
112 f := err.Error
113 if got := f(); got != "ok" {
114 panic(got)
115 }
116
117 err = nil
118 if got := f(); got != "ok" {
119 panic(got)
120 }
121
122 defer func() {
123 r := fmt.Sprint(recover())
124
125 if r != "interface conversion: interface is nil, not error" &&
126 r != "runtime error: invalid memory address or nil pointer dereference" &&
127 r != "method value: interface is nil" {
128 panic("want runtime panic from nil interface method value, got " + r)
129 }
130 }()
131 f = err.Error
132 panic("unreachable")
133 }
134
135 func main() {
136 valueReceiver()
137 pointerReceiver()
138 addressibleValuePointerReceiver()
139 promotedReceiver()
140 anonStruct()
141 typeCheck()
142
143 if e := regress1(errString("hi"))(); e != "hi" {
144 panic(e)
145 }
146
147 nilInterfaceMethodValue()
148 }
149
View as plain text