go - 在 Go 中使用互斥锁

标签 go

我正在尝试了解互斥锁的工作原理。据我目前的理解,它是为了进行原子操作并同步对某些数据的访问。

我在这里构建了一个队列数据结构的例子:https://github.com/arnauddri/algorithms/blob/master/data-structures%2Fqueue%2Fqueue.go

这里是一些代码:

package queue

import "sync"

type Queue struct {
    queue []interface{}
    len   int
    lock  *sync.Mutex
}

func New() *Queue {
    queue := &Queue{}
    queue.queue = make([]interface{}, 0)
    queue.len = 0

    return queue
}

func (q *Queue) Push(el interface{}) {
    q.lock.Lock()
    defer q.lock.Unlock()

    q.queue = append(q.queue, el)
    q.len++
}

但是,当我尝试创建队列并将项目推送到其中时,出现运行时错误:

q := New()
q.Push(1)

panic: runtime error: invalid memory address or nil pointer dereference [recovered]
panic: runtime error: invalid memory address or nil pointer dereference

我真的不明白这里发生了什么。

这里应该如何使用Mutex?

非常感谢

最佳答案

你得到那个错误是因为你没有分配任何互斥锁,你只有一个指向互斥锁的指针。 互斥量通常在结构内部声明并且没有指针。请参阅下面的工作示例:

http://play.golang.org/p/8LF3yVOkSW

import "sync"

type Queue struct {
    len int

    lock  sync.Mutex // add it before the fields that are being protected by the mutex
    queue []interface{}
}

func New() *Queue {
    queue := &Queue{}
    queue.queue = make([]interface{}, 0)
    queue.len = 0

    return queue
}

func (q *Queue) Push(el interface{}) {
    q.lock.Lock()
    defer q.lock.Unlock()

    q.queue = append(q.queue, el)
    q.len++
}

func main() {
    q := New()
    q.Push(1)
}

关于go - 在 Go 中使用互斥锁,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/28243409/

相关文章:

go - Go程序"Import cycle not allowed"错误

go - 在运行时转储 Go 进程的堆

go - 动态添加Kafka主题以从中使用,而无需重新启动GoLang应用程序

go - golang中 slice 的cap vs len

go - 将 go 接口(interface)对象转换/类型转换为具体类型

sql - 更快的 sqlite3 查询?我需要尽快处理 100 万行

Go SSH key 不能与 crypto/ssh 一起使用,但可以手动使用

go - pubsub.NewClient 卡在开发机器和 docker 中

go - 在没有根文件夹的文件夹中压缩内容

function - 在 golang 中,使用 net/http 时如何调用带和不带尾随括号的函数