C++ TCP客户端网络消息发送接收同步实现
废话不多说, 直入主题, 我们在写客户单的时候希望在哪里发消息出去,然后在哪里返回消息(同步), 然后继续往下运行-, 而不是在这里发送了一个消息给服务端, 在另一个地方接受消息(异步) , 也不知道等多久, 才收到消息, 等收到消息在通知发送消息的地方, 让程序继续往下运行, 这样想想异步实在太麻烦了,
实现同步的思想: 1 将socket设置成阻塞的, 2: 设置接受超时, 3: 消息类型区分
直接上代码
封装socket 头文件
#pragma once #include <string> #include <Winsock2.h> using namespace std; class TcpSocket { public: TcpSocket(); ~TcpSocket(); bool SocketInit(); bool CreatSocket(string strIp, int nPort); bool SendMsg(int msgType, string strSendBuf, string& strRecvMsg, int iTimeOut); private: SOCKET m_Scoket; DWORD m_dwVserion; WSADATA m_WsData; int m_iError; bool m_isSocketFlag; };
socket封装实现
#include "TcpSocket.h" #pragma comment(lib, "ws2_32.lib") #pragma warning(disable:4996) TcpSocket::TcpSocket() { m_dwVserion = 0; m_isSocketFlag = true; memset(&m_WsData, 0, sizeof(WSADATA)); } TcpSocket::~TcpSocket() { closesocket(m_Scoket); WSACleanup(); } bool TcpSocket::SocketInit() { m_dwVserion = MAKEWORD(1, 1); m_iError = WSAStartup(m_dwVserion, &m_WsData); if (m_iError != 0) { printf("socket 初始化操作失败"); m_isSocketFlag = false; } if (LOBYTE(m_WsData.wVersion) != 1 && HIBYTE(m_WsData.wVersion) != 1) { WSACleanup(); m_isSocketFlag = false; } return m_isSocketFlag; } bool TcpSocket::CreatSocket(string strIp, int nPort) { if (!m_isSocketFlag) return false; m_Scoket = socket(AF_INET, SOCK_STREAM, 0); SOCKADDR_IN addr; addr.sin_addr.S_un.S_addr = inet_addr(strIp.c_str()); addr.sin_family = AF_INET; addr.sin_port = htons(nPort); m_iError = connect(m_Scoket, (SOCKADDR*)&addr, sizeof(SOCKADDR)); if(m_iError != 0) m_isSocketFlag = false; return m_isSocketFlag; } bool TcpSocket::SendMsg(int MsgType, string strSendBuf, string& strRecvMsg, int iTimeOut) { if (!m_isSocketFlag) return false; int timeOut = iTimeOut * 1000 ; //秒 setsockopt(m_Scoket, SOL_SOCKET, SO_SNDTIMEO, (char*)&timeOut, sizeof(timeOut)); setsockopt(m_Scoket, SOL_SOCKET, SO_RCVTIMEO, (char*)&timeOut, sizeof(timeOut)); printf("开始发送消息\n"); int iRet = send(m_Scoket, strSendBuf.c_str(), strSendBuf.length(), 0); if (iRet == 0) { printf("发送消息超时\n"); return false; } printf("发送消息: %s\n", strSendBuf.c_str()); char recvBuf[1024] = { 0 }; iRet = recv(m_Scoket, recvBuf, sizeof(recvBuf), 0); if (iRet == -1) { printf("接受消息超时\n"); return false; } string recvMsg = string(recvBuf); if (recvMsg.find(to_string(MsgType)) == string::npos) return false; strRecvMsg = string(recvBuf); return true; }
测试程序:
#include <stdio.h> #include "TcpSocket.h" int main() { TcpSocket client; bool isRet = client.SocketInit(); if (!isRet) return 0; isRet = client.CreatSocket("10.1.1.66", 2345); if (isRet) { while(1) { string strRecv = string(); client.SendMsg(1, string("Hello"), strRecv, 5); printf("接受消息: %s\n", strRecv.c_str()); Sleep(200); } } getchar(); return 0; }
以上是个人拙见, 若有更好的方法请指教小弟, 谢谢! 谢谢! 谢谢!