[英]socket: multithreading doesn't work when client reads messages
我有一台服务器,可以接受两个套接字连接。 它为每个套接字创建一个线程,以便可以并行发送消息。
现在,我正在尝试编码我的客户端。
我创建一个名为SocketThread
的类作为套接字线程。 这是主要代码:
void SocketThread::ReadData()
{
int n = 0;
while (!finished)
{
while ((n = read(sockfd, recvBuff, sizeof(Data))) > 0)
{
std::cout<<std::this_thread::get_id()<<std::endl;
std::this_thread::sleep_for(std::chrono::milliseconds(2000));
}
}
}
std::thread SocketThread::run()
{
return std::thread([=] { ReadData(); });
}
在函数main
:
SocketThread s0("127.0.0.1", 10000);
SocketThread s1("127.0.0.1", 10000);
std::thread td0{sts[0].run()};
std::thread td1{sts[1].run()};
td0.join(); // stop here
td1.join();
// something else
当我执行程序时,它将在td0.join();
处td0.join();
,这意味着我可以在控制台上获取线程td0
的ID,而从不获取其他线程。
但是,当我删除(n = read(sockfd, recvBuff, sizeof(Data))) > 0
,这意味着现在客户端只是一个简单的线程,它不会接收任何东西,一切都会好起来- -我可以得到两个线程的两个ID。
为什么?
编辑看来我以前join
不正确。
我需要的是main
直到两个线程一起获得1000个字符后才执行//something else
。
我该怎么办?
您没有错误地使用join()
。 如果要让main()
阻塞直到两个线程结束,则您的代码是正确的: td0.join()
将阻塞直到线程td0
结束,并且与td1
相同。
现在,如果您希望线程在接收到sizeof(Data)
个字节后结束,则函数void SocketThread::ReadData()
应该看起来像这样:
void SocketThread::ReadData()
{
int n, total = 0;
while (!finished)
{
while ((n = read(sockfd, &recvBuff[total], sizeof(Data) - total)) > 0)
{
total += n;
}
if (n == -1)
{
// manage error here
}
if (n == 0)
{
std::cout << "client shut the socket down; got " << total << " bytes over " << sizeof(Data) << std::endl;
finished = true;
}
}
}
简短的说明:不能保证您可以通过一次read()
操作获得客户端发送的所有数据,因此您需要调用read()
并将数据累积到缓冲区中,直到返回值为0
(即客户端关闭套接字)。 read(sockfd, &recvBuff[total], sizeof(Data) - total)
确保传入的数据正确地附加在缓冲区的正确位置。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.