具有阻塞recv()和非阻塞send()的Winsock2套接字

时间:2017-07-24 17:49:31

标签: c++ multithreading client-server winsock2

我正在开发一个简单的1v1(实时)砖块破坏者游戏,以提高我的编程技巧。 它基于服务器 - 客户端模型,我使用<winsock2.h><thread><mutex>库来实现。 在客户端,我想从不同的线程调用send()和recv()函数(来自main()线程的send(),而来自另一个线程的recv())。 我已经意识到,如果recv()函数阻塞,那将是最好的,而send()是非阻塞的。 我听说在winsock2中创建这样的套接字是不可能的。但是,我提出了一个想法,想知道,如果这是一个不好的做法: 我用阻塞套接字连接到服务器。当一个重要的用户事件发生时,我创建了一个分离的线程,它调用发送者函数(将用户的事件交给服务器),而不是从主线程调用sender方法。

使用std::mutex,我可以保证一次只能使用一种发送方法。例如:

#include <mutex>
#include <string>

class Connection
{
   std::mutex senderMutex
   // other member variables

   void sendMessage(std::string& msg)
   {
      std::lock_guard<std::mutex> lg(senderMutex);
      // some code     
   }

   void sendUserAction(Action& action)
   {
      std::lock_guard<std::mutex> lg(senderMutex);
      // some code
   }

   // other member functions
};

从主线程:

if (userEventHappened)
{
   switch(userEvent)
   {
   case ChatMessage:
       std::thread(&Connection::sendMessage, &connection /* an instance of Connection*/, std::ref(message)).detach();
       break;
   case UserAction:
       std::thread(&Connection::sendUserAction, &connection, std::ref(action)).detach();
       break;
   }
}

由于这是一个砖块破坏者游戏,玩家必须移动自己的球拍,因此有许多用户动作,因此可以在短时间内创建太多线程。 我很好奇,如果从分离的线程调用send()方法是危险的和/或不好的做法,或者是否有更好的解决方案。 我也不清楚它是否会导致大多数线程被senderMutex阻止的性能问题。

0 个答案:

没有答案