必须先启动一个选择服务器再 启动一个选择客服端 然后不能两个同时选择接受。。。。真吭人是吧没办法 啊
#pragma once
#define MSG_SIZE 100 //消息的最大值
#include <iostream>
#include <string>
#include <vector>
#include <WinSock2.h>
#pragma comment(lib,"wsock32.lib")
using namespace std;
class YdcSocket
{
public:
YdcSocket()
{}
void InitYdcSocket(bool isServer)
{
//初始化套接字动态库
if ( WSAStartup(MAKEWORD(2,2),&wsd)!=0 ){ErrorMsg.push_back("WSAStartup failed!");}
if (isServer)
{
//创建套接字
sServer = socket(AF_INET,SOCK_STREAM ,IPPROTO_TCP);
if (INVALID_SOCKET == sServer){ErrorMsg.push_back("socket failed!");}
//服务器套接字地址
addrServ.sin_family = AF_INET;
cout<<"正在启动服务器"<<endl;
addrServ.sin_port = htons(4999);
addrServ.sin_addr.s_addr = INADDR_ANY;
Bind();Listen();Accept();
}else
{
//创建套接字
sClient = socket(AF_INET,SOCK_STREAM ,IPPROTO_TCP);
if (INVALID_SOCKET == sServer){ErrorMsg.push_back("socket failed!");}
//服务器套接字地址
addrServ.sin_family = AF_INET;
cout<<"正在启动客服端"<<endl;
addrServ.sin_port = htons((short)4999);
addrServ.sin_addr.s_addr = inet_addr("127.0.0.1");
Connect();
}
}
~YdcSocket(void){}
public:
void strat()
{
while (1)
{
cin.clear();
int n = 0;
cout<<"1 发送 2 接收 其他 查看错误日志"<<endl;
cin>>n;
switch (n)
{
case 1://发送
cout<<"请输入你要发送的消息"<<endl;
cin>>msg;
Send();
break;
case 2://接收
msg = "";
cout<<"你将接收消息"<<endl;
Recv();
cout<<"你接受到的消息是:"<<msg<<endl;
break;
default:
ShowError();
break;
}
}
}
void Recv()
{
ZeroMemory(buf,MSG_SIZE);
if (SOCKET_ERROR == recv(sClient,buf,MSG_SIZE,0))
{
ErrorMsg.push_back("非法关闭 failed!");
closesocket(sServer);
closesocket(sClient);
WSACleanup();
}else if (retVal == 0)
{
ErrorMsg.push_back("正常关闭 failed!");
closesocket(sServer);
closesocket(sClient);
WSACleanup();
}
msg = buf;
}
void Send()
{
cout<<strlen(msg.c_str());
if (SOCKET_ERROR == send(sClient,msg.c_str(),strlen(msg.c_str()),0))
{
ErrorMsg.push_back("send failed!");
closesocket(sClient);
WSACleanup();
}
}
private:
vector<string> ErrorMsg; //错误消息
string msg; //消息
char buf[MSG_SIZE]; //发送的消息
WSADATA wsd; //WSADATA变量
SOCKET sServer; //服务器套接字
SOCKET sClient; //客服端套接字
SOCKADDR_IN addrServ; //服务器地址
int retVal; //还回值
private:
void Bind()
{
if (SOCKET_ERROR == ::bind(sServer,(LPSOCKADDR)&addrServ,sizeof(SOCKADDR_IN)))
{
ErrorMsg.push_back("1 failed!");
::closesocket(sServer);
WSACleanup();
}
}
void Listen()
{
if (::listen(sServer, SOMAXCONN) == SOCKET_ERROR){
ErrorMsg.push_back("2 failed!");
::closesocket(sServer);
WSACleanup();
}
}
void Accept()
{
cout<<"等待客服"<<endl;
int m_addrLen = sizeof(addrServ);
sClient = ::accept(sServer,(SOCKADDR*)&addrServ, &m_addrLen);
if (sClient == INVALID_SOCKET){
ErrorMsg.push_back("3 failed!");
::closesocket(sClient);
WSACleanup();
}
}
void Connect()
{
//这里需要
if (SOCKET_ERROR == ::connect(sClient, (LPSOCKADDR)&addrServ, sizeof(SOCKADDR_IN) ) ){
ErrorMsg.push_back("4 failed!!");
::closesocket(sClient);
WSACleanup();
}
}
void ShowError()
{
for (int i =0 ; i < ErrorMsg.size() ; i++)
{
cout<<ErrorMsg.at(i)<<endl;
}
}
};
// Socket类.cpp : 定义控制台应用程序的入口点。
//
#include "stdafx.h"
#include "YdcSocket.h"
int _tmain(int argc, _TCHAR* argv[])
{
YdcSocket y;
int n;
cout<<"请输入 1 选择为服务器 0 为客服端"<<endl;
cin>>n;
y.InitYdcSocket(n);
y.strat();
system("pause");
return 0;
}
然后呢我就想 要是能否有多人 随意点就好了 想发就发想收就收 那该多好 啊 。。
就想到了 多线程 结果发现 这个 是 阻塞的 (好乱的 )
就找到了
winsock I/O模型
。。。简单的 就是select 模型:了 呵呵 再写写