RT。。。就是网络编程课的任务啊、
写了一个服务器与客户端的控制台程序,实现一来一回的即时聊天,可显示发送时间,以关键字bye结束连接
遗憾的是也只能一来一回,不能某端连续发送消息
在执行监听函数的时候就不能执行输入,或者这就是黑屏程序吧…
查了下貌似其实也能做到,利用多线程?不过现在没去找资料学习了
明天就是上机课,这个实验一任务截止,先把代码po到博客里。
#include
#include
#include
#include
#pragma comment (lib,"Ws2_32.lib")
#define NUM 10 // 最大客户端连接数
void END(SOCKET &ListenSocket,SOCKET &ClientSocket) // 释放相关资源
{
closesocket(ListenSocket);
closesocket(ClientSocket);
WSACleanup();
}
void OutputTime()
{
time_t T;
struct tm *p;
time (&T);
p = localtime(&T);
printf("%d/%02d/%02d %02d:%02d:%02d\n\n",1900+p->tm_year,1+p->tm_mon,p->tm_mday,p->tm_hour,p->tm_min,p->tm_sec);
}
int main()
{
system("title 服务器端");
system("mode con cols=49 lines=30");
char servername[100]={"Server"}; // 存储服务器名称
char clientname[100]={0};
WSADATA wsaData;
char buf[100]={0}; //发送数据缓冲区
char getbuf[100]={0}; //接收数据缓冲区// 创建类型为WSADATA的对象
int iResult = WSAStartup(MAKEWORD(2,2),&wsaData); // 初始化winsock并根据返回值判断错误信息
if(iResult!=0)
{
printf("初始化失败。错误代码:%d\n",iResult);
return 1;
}
SOCKET ListenSocket,ClientSocket; // 定义监听和通信套接字
ListenSocket = socket(AF_INET,SOCK_STREAM,0); // 定义此Socket所使用的通信协议:IPV4地址族、流式套接字、不指定通信协议
sockaddr_in addr,addr2; // 定义套接字地址结构
addr.sin_family = AF_INET; // 初始化地址结构
addr.sin_port = htons(75);
addr.sin_addr.S_un.S_addr = INADDR_ANY;
int addr2Len = sizeof(addr2); // 获取套接字地址结构大小
bind(ListenSocket, (sockaddr*)&addr, sizeof(addr) ); // 绑定套接字
listen(ListenSocket,NUM); // 监听套接字,最大连接数为10
if(iResult==0)
{
printf("服务器初始化完成\n");
}
char str[] = "\n正在等待客户端连接...\n";
for(int i=0;str[i]!='\0';i++) // 以打字机效果输出等待提示信息
{
printf("%c",str[i]);
Sleep(35);
}
ClientSocket = accept(ListenSocket, (sockaddr*)&addr2, &addr2Len); // 服务器端接受客户端的连接请求
if(ClientSocket != NULL)
{
printf(" 客户端已连接至服务器,客户端IP:%s\n", inet_ntoa(addr2.sin_addr) );
}
iResult=send(ClientSocket,servername,sizeof(servername),0); // 发送服务器名称至客户端
if(iResult==SOCKET_ERROR)
{
printf("\n 连接至客户端失败,连接断开...\n");
END(ListenSocket,ClientSocket);
return 1;
}
iResult=recv(ClientSocket,clientname,sizeof(clientname),0); // 接收客户端名称
if(iResult==SOCKET_ERROR)
{
printf("\n 客户端通讯返回失败,连接断开...\n");
END(ListenSocket,ClientSocket);
return 1;
}
printf("\n---输入需要发送的信息,键入关键词bye以结束会话---\n\n");
char wait[]="[正在输入...]";
while(1) // 持续发送接收消息
{
printf("%s:",servername);
gets(buf);
OutputTime();
iResult=send(ClientSocket,buf,sizeof(buf),0); // 向客户端发送信息,函数调用方式与write()无异
if(iResult==SOCKET_ERROR)
{
printf("----------------连接断开,发送失败---------------\n\n");
END(ListenSocket,ClientSocket);
break;
}
if(strcmp(buf,"bye")==0)
{
printf("------------------您已结束会话-------------------\n\n");
END(ListenSocket,ClientSocket);
break;
}
memset(buf,0,sizeof(buf));
printf("%s:%s",clientname,wait);
iResult=recv(ClientSocket,getbuf,sizeof(getbuf),0); // 接收数据
if(iResult==SOCKET_ERROR)
{
printf(" 接收失败,连接断开...\n");
printf("----------------连接断开,接收失败---------------\n\n");
END(ListenSocket,ClientSocket);
break;
}
printf("\r%s:%s \n",clientname,getbuf);
OutputTime();
if(strcmp(getbuf,"bye")==0)
{
printf("----------------对方结束了会话-------------------\n\n");
END(ListenSocket,ClientSocket);
break;
}
memset(getbuf,0,sizeof(getbuf));
}
return 0;
}
#include
#include
#include
#include
#pragma comment (lib,"Ws2_32.lib")
#define TIMES 7 // 最大重连次数
void END(SOCKET &s) // 释放相关资源
{
closesocket(s);
WSACleanup();
}
void OutputTime()
{
time_t T;
struct tm *p;
time (&T);
p = localtime(&T);
printf("%d/%02d/%02d %02d:%02d:%02d\n\n",1900+p->tm_year,1+p->tm_mon,p->tm_mday,p->tm_hour,p->tm_min,p->tm_sec);
}
int main()
{
system("title 客户端");
system("mode con cols=49 lines=30");
char servername[100]={0}; // 存储发送给客户端的信息
char clientname[100]={"Client"};
WSADATA data;
char buf[100]={0}; //发送数据缓冲区
char getbuf[100]={0}; //接收数据缓冲区
int iResult = WSAStartup(MAKEWORD(2,2),&data);
if(iResult!=0)
{
printf("初始化版本号失败!");
return -1;
}
SOCKET s; //创建套接字
s=socket(AF_INET,SOCK_STREAM,0);
if(s==INVALID_SOCKET)
{
printf(" 创建套接字失败...\n");
return 0;
}
sockaddr_in addr; //定义套接字地址结构
addr.sin_family=AF_INET; //初始化地址结构
addr.sin_port=htons(75);
addr.sin_addr.S_un.S_addr=inet_addr("127.0.0.1");
printf("客户端初始化完成\n");
char str[] = "\n正在连接服务器...";
for(int i=0;str[i]!='\0';i++) // 以打字机效果输出等待提示信息
{
printf("%c",str[i]);
Sleep(35);
}
int TRY=0; // 初始化连接次数
while(1) // 反复连接服务器直到成功或达到最大次数
{
iResult=connect(s,(sockaddr*)&addr,sizeof(addr)); // 连接服务器
if(iResult==SOCKET_ERROR && TRY>=TIMES)
{
printf("\n 连接服务器失败!\n");
return 1;
}
else if(iResult==SOCKET_ERROR)
{
TRY++;
printf("\r连接失败!正在尝试重连...(%d/%d)",TRY,TIMES);
Sleep(1000); // 1秒后再次重连
}
else if(iResult==0)
{
printf("\n 客户端已成功与服务器建立通讯\n");
break;
}
}
iResult=recv(s,servername,sizeof(servername),0); // 接收服务器名称
if(iResult==SOCKET_ERROR)
{
printf(" 接收服务器数据失败,连接断开...\n");
return 1;
}
iResult=send(s,clientname,sizeof(clientname),0); // 发送客户端名称至服务端
if(iResult==SOCKET_ERROR)
{
printf(" 发送数据失败,连接断开...n");
return 1;
}
printf("\n---输入需要发送的信息,键入关键词bye以结束会话---\n\n");
char wait[]="[正在输入...]";
while(1)
{
printf("%s:%s",servername,wait);
iResult=recv(s,getbuf,sizeof(getbuf),0); // 接收数据
if(iResult==SOCKET_ERROR)
{
printf("\n\n---------------与服务器的连接断开----------------\n\n");
END(s);
break;
}
printf("\r%s:%s \n",servername,getbuf);
OutputTime();
if(strcmp(getbuf,"bye")==0)
{
printf("----------------对方结束了会话-------------------\n\n");
END(s);
break;
}
memset(getbuf,0,sizeof(getbuf));
printf("%s:",clientname);
gets(buf);
OutputTime();
iResult=send(s,buf,sizeof(buf),0);
if(iResult==SOCKET_ERROR)
{
printf("----------------连接断开,发送失败---------------\n\n");
END(s);
break;
}
if(strcmp(buf,"bye")==0)
{
printf("------------------您已结束会话-------------------\n\n");
END(s);
break;
}
memset(buf,0,sizeof(buf));
}
return 0;
}