[英]Threaded Socket.Send()
我有2个线程同时运行,每个线程都正在写入socket.Send()流,
While (soc.Connected)
{
byte[] byData = new byte[2];
byData = System.Text.Encoding.ASCII.GetBytes("A");
soc.Send(BitConverter.GetBytes(byData.Length));
soc.Send(byData);
}
另一个线程使用完全相同的代码,除了发送“ 1”而不是“ A”。
另一端的数据如何? 它是AAAAAAAA还是111111111s的流,还是像A1A1111AAAA1这样的随机混合流?
我是否应该避免完全发送这种方式,并在其他线程完成之前阻止发送?
我是否应该避免完全发送这种方式,并在其他线程完成之前阻止发送?
是的,不是,您应该完全避免这种情况,但是没有必要在其他线程完成之前阻止发送。
您可以做的是让第三个线程负责发送数据,而需要发送数据的两个线程将其数据放入线程安全队列中。 然后,发送线程将使要完成的工作出队,并通过网络将其发送出去。
const int MAX_QUEUE_LENGTH = 10;
private BlockingCollection<MyMessageContainer> messageQueue = new BlockingCollection<MyMessageContainer>(new ConcurrentQueue<MyMessageContainer>(), MAX_QUEUE_LENGTH);
void ProcessMessages()
{
foreach (var message in messageQueue.GetConsumingEnumerable())
{
if(soc.Connected == false)
break;
soc.Send(message.ToPaylod());
}
}
void GenerateMessageOne()
{
while(true)
{
messageQueue.Add(new MyMessageContainer("A"));
}
}
void GenerateMessageTwo()
{
while(true)
{
messageQueue.Add(new MyMessageContainer("1"));
}
}
class MyMessageContainer
{
public MyMessageContainer(string message)
{
_message = message;
}
private string _message;
public byte[] ToPayload()
{
var lengthBytes = BitConverter.GetBytes(byData.Length);
return lengthBytes.Concat(() => System.Text.Encoding.ASCII.GetBytes(_message)).ToArray();
}
}
上面的代码将使两个线程同时工作,而不会阻塞,直到队列的长度达到MAX_QUEUE_LENGTH
为止,一旦调用messageQueue.Add(
现在将开始阻塞,直到发送线程有机会清理一些空间为止腾出空间后,它将取消阻止其中一项功能,并使其继续运行。
如果要随机排序的输出,最简单的解决方案是在实际写入套接字的行周围放一个锁。 为了公平起见,我还建议添加对Thread.Sleep的调用,尽管这是可选的。
While (soc.Connected)
{
byte[] byData = new byte[2];
byData = System.Text.Encoding.ASCII.GetBytes("A");
lock(soc)
{
soc.Send(BitConverter.GetBytes(byData.Length));
soc.Send(byData);
}
Thread.Sleep(0);
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.