1 回答

TA貢獻1827條經驗 獲得超4個贊
要檢查一個io.Reader(或任何其他接口)值是否為nil,您只需將它與 進行比較nil。
非nil io.Reader- 是否是有意義的實現,這是另一個問題。
例如,這個實現有意義嗎?
type panicReader struct{}
func (panicReader) Read(p []byte) (int, error) {
panic("foo")
}
panicReader當然 implements io.Reader,但是每當你調用它的Read()方法時,它總是會 panic。
有bytes.Buffer。指向它的指針 implements io.Reader。但是調用指針值會出現恐慌Buffer.Read()。nil *bytes.Buffer但這不是因為您不能在nil指針接收器上調用方法,而是因為 的實現bytes.Buffer.Read()試圖取消引用指針接收器,而這種取消引用操作是導致恐慌的原因:
// Excerpt from bytes.Buffer.Read implementation
func (b *Buffer) Read(p []byte) (n int, err error) {
b.lastRead = opInvalid
if b.empty() {
// ...
}
您不能在這里做出一般性結論(目前)??吹竭@個io.Reader實現:
type myBuffer struct{}
var count int
func (*myBuffer) Read(p []byte) (int, error) {
if len(p) > 0 {
count++
if count >= 10 {
return 0, io.EOF
}
p[0] = 'a'
return 1, nil
}
return 0, nil
}
*myBufferimplements io.Reader,它的Read()方法不使用指針接收器值。這是什么意思?您可以調用Read()一個nil *myBuffer值:
var data *myBuffer
request := &Request{
Body: data,
}
if request.Body != nil {
data, err := ioutil.ReadAll(request.Body)
fmt.Println(string(data), err)
}
這將輸出(在Go Playground上嘗試):
aaaaaaaaa <nil>
所以結論是這樣的:通常具有指針接收器方法的類型需要非nil指針,因為它們使用指向對象(如果bytes.Buffer它們使用指向結構的字段)。要使用此類類型(對已實現的接口進行有意義的實現),您通常需要一個非nil指針值來使方法“工作”。myBuffer然而,正如上面的實現所示,這并不總是一個要求。始終閱讀所用類型和方法的文檔以避免此類誤用(例如嘗試使用 a nil *bytes.Buffer)是您的工作。
- 1 回答
- 0 關注
- 156 瀏覽
添加回答
舉報