Golang net.Conn 并行写入 [英] Golang net.Conn Write in parallel
问题描述
我有多个 Goroutine 共享一个 net.Conn 对象.他们可以同时发出 Write 调用吗?
I have multiple Goroutines sharing a net.Conn object. Can they issue a Write calls simultaneously?
我主要关心的是部分完成的写入调用.假设我打算写 100 个字节,但只发送了 30 个,所以我需要再发送 70 个.为此,我通常会编写一个循环:
My main concern is that of Write calls which are partially done. Say I intend to wrote 100 bytes, but only 30 were sent, so I need to send 70 more. For this I will typically write a loop:
count := 0
for count < len(buf) {
byteSent, err := conn.Write(buf[count:])
//check error
count += byteSent
}
但我看到 Go 在 net.Conn.Write 行号中实现了这个循环318,它通过锁定来实现.
But I see that Go implements this loop in net.Conn.Write line number 318 and it does so by taking a lock.
但是,在 Windows 实现上没有这样的循环,除了有一个调用到 WSASend.我不知道 WSASend 的行为方式,也无法从 MSDN 文档中获得太多信息
However, on Windows implementation there is no such loop except that there is a call to WSASend. I do not know how WSASend behaves and could not get much from the MSDN docs
因此问题是:
添加第四个问题
- 每次写入套接字时都需要获取锁吗?
- 如果是,那么在 Write 实现中获取锁的目的就失效了.
- 在 unix 实现中,是否意味着我无法获取 byteSent <len(buf) 除非 err != nil?(我的意思是我读的代码正确吗?)
- Windows 上的 WSASend 是否实现了 Unix 实现中的等效循环
推荐答案
io.Write 说在部分写入的情况下,err将是 != nil
The io.Write says that in case of partial write, err will be != nil
找到这里在 StackOverflow 上,WSASend 不需要有一个循环.
Found here on StackOverflow that WSASend need not have a loop around it.
来自#1 ,这意味着我不需要在调用 net.Conn.Write 之前获取锁.
From #1 & #2, it implies that I need not acquire lock before calling net.Conn.Write.
所以我的问题得到了回答.
So my question stands answered.
这篇关于Golang net.Conn 并行写入的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!