英文:
Go linked list pointer assignment from non-pointer struct element
问题
你好!以下是你提供的代码的翻译:
我在Go语言中遇到了一个“无法分配给指针”的错误,很困惑。
这是可以工作的代码:http://play.golang.org/p/P9FjK8A-32,与Go的原始container/list代码相同。
type List struct {
root Element
len int
}
type Element struct {
next, prev *Element
list *List
Value interface{}
}
原始代码将root
定义为值,并在需要指针类型时引用它,但为什么不一开始就将root
定义为指针呢?
type List struct {
root *Element
len int
}
type Element struct {
next, prev *Element
list *List
Value interface{}
}
这样会导致错误:http://play.golang.org/p/1gCAR_rcx1 -> invalid memory address or nil pointer dereference
。
为什么会出现这个错误?
为什么Go在定义next
和prev
时使用指针,而在定义root
时不使用指针?
谢谢!
英文:
https://github.com/golang/go/blob/master/src/container/list/list.go#L49
I am having hard time why I am getting cannot assign to pointer
error in Go.
Here's the code that works: http://play.golang.org/p/P9FjK8A-32 which is same as Go's original container/list code
type List struct {
root Element
len int
}
type Element struct {
next, prev *Element
list *List
Value interface{}
}
The original code has root
as a value and reference it everytime it needs to be in pointer type but why not at first place define root
as a pointer?
type List struct {
root *Element
len int
}
type Element struct {
next, prev *Element
list *List
Value interface{}
}
This give me an error: http://play.golang.org/p/1gCAR_rcx1 -> invalid memory address or nil pointer dereference
Why am I getting this error?
Why does Go define root
as a non-pointer value when it defines next
, and prev
as pointers?
Thanks
答案1
得分: 1
指针默认为nil
,需要进行初始化。
原始代码:
// Init initializes or clears list l.
func (l *List) Init() *List {
l.root.next = l.root
l.root.prev = l.root
l.len = 0
return l
}
应改为:
// Init initializes or clears list l.
func (l *List) Init() *List {
l.root = new(Element) // 为了避免解引用空指针,需要进行初始化
l.root.next = l.root
l.root.prev = l.root
l.len = 0
return l
}
示例代码可在 http://play.golang.org/p/EYSscTMYnn 查看。
在标准库的情况下,root
不需要是指针,但对于prev
和next
来说是必需的,否则结构体定义将会是递归的,这是不允许的,因为理论上会导致无限大小的结构体...
英文:
A pointer is nil
by default and needs to be initialized.
This:
// Init initializes or clears list l.
func (l *List) Init() *List {
l.root.next = l.root
l.root.prev = l.root
l.len = 0
return l
}
should become this:
// Init initializes or clears list l.
func (l *List) Init() *List {
l.root = new(Element) // necessary to avoid dereferencing a nil pointer
l.root.next = l.root
l.root.prev = l.root
l.len = 0
return l
}
Demo at http://play.golang.org/p/EYSscTMYnn
In the case of the standard library, it is not necessary to have root
be a pointer, however, for prev
and next
it is necessary, otherwise the struct definition would be recursive, which is not allowed, because it would in theory cause a struct of infinite size...
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论