网络编程;套接字;TCP通讯;UDP通讯;0909

发布于:2025-09-10 ⋅ 阅读:(19) ⋅ 点赞:(0)

思维导图

TCP服务器端和客户端通讯

服务器端 代码

#include<myhead.h>
#define SER_IP "192.168.109.12"//我的虚拟机的ip
#define SER_PORT 8888
int main()
{
	//1.创建一个用于连接的套接字文件描述符
	int sfd = socket(AF_INET,SOCK_STREAM,0);
	if(sfd==-1)
	{
		perror("socket error");
		return -1;
	}
	printf("sfd = %d\n",sfd);
	//2.给套接字绑定ip地址和的端口号
	//2.1准备地址信息结构体
	struct sockaddr_in sin;
	//通信域地址族
	sin.sin_family = AF_INET;
	//服务器端口号
	sin.sin_port = htons(SER_PORT);//2字节 主机字节序 转化为 网络字节序
	//服务器ip地址
	sin.sin_addr.s_addr = inet_addr(SER_IP);//ip地址 点分十进制 转化为 网络字节序
	//2.2执行绑定工作
	if(bind(sfd,(struct sockaddr*)&sin,sizeof(sin))==-1)
	{
		perror("bind error");
		return -1;
	}
	printf("bind success\n");
	//3.将套接字设置成被动监听状态
	if(listen(sfd,128)==-1)
	{
		perror("listen error");
		return -1;
	}
	printf("listen success\n");
	//4.阻塞 等客户端的连接
	//4.1 定义地址信息结构体,用于客户端地址信息
	struct sockaddr_in cin;
	socklen_t addrlen = sizeof(cin);//接收地址长度
	int newfd = accept(sfd,(struct sockaddr*)&cin,&addrlen);
	if(newfd==-1)
	{
		perror("accept error");
		return -1;
	}
	printf("[%s:%d]-连接成功newfd = %d\n",\
			inet_ntoa(cin.sin_addr),\
			ntohs(cin.sin_port),newfd);
	//5.实现数据的收发
	char buf[128]="";
	while(1)
	{
		//清空buf
		bzero(buf,sizeof(buf));
		//从套接字读取消息
		int res=read(newfd,buf,sizeof(buf));
		if(res==0)
		{
			printf("客户端下线\n");
			close(newfd);//关闭通信套接字
			break;
		}
		printf("[%s:%d] : %s\n",\
				inet_ntoa(cin.sin_addr),\
				ntohs(cin.sin_port),buf);
		//给消息 加个:D还回去
		strcat(buf,":D");
		write(newfd,buf,strlen(buf));
		printf("发送成功\n");
	}
	//6.关闭套接字
	close(sfd);

	return 0;
}

客户端 代码

#include<myhead.h>
#define SER_IP "192.168.109.12"    //服务器ip地址
#define SER_PORT 8888               //服务器端口号
#define CLI_IP "192.168.109.12"     //客户端ip地址
#define CLI_PORT 7777               //客户端端口号


int main(int argc, const char *argv[])
{
        //1、创建用于通信的套接字文件描述符
        int cfd = socket(AF_INET, SOCK_STREAM, 0);
        if(cfd == -1)
        {
                perror("socket error");
                return -1;
        }

        //2、给客户端套接字绑定ip地址和端口号
        //2.1 填充地址信息结构体
        struct sockaddr_in cin;
        cin.sin_family = AF_INET;
        cin.sin_addr.s_addr = inet_addr(CLI_IP);
        cin.sin_port = htons(CLI_PORT);
        //2.2 绑定
        if(bind(cfd, (struct sockaddr*)&cin, sizeof(cin))==-1)
        {
                perror("bind error");
                return -1;
        }


        //3、连接服务器
        //3.1 组装对端地址信息结构体
        struct sockaddr_in sin;
        sin.sin_family = AF_INET;    //通信域
        sin.sin_addr.s_addr = inet_addr(SER_IP);   //要连接的服务器ip
        sin.sin_port = htons(SER_PORT);     //服务器的端口号
        //3.2 连接操作
        if(connect(cfd, (struct sockaddr*)&sin, sizeof(sin))==-1)
        {
                perror("connect error");
                return -1;
        }


        //4、数据通信
        char buf[128] = "";
        while(1)
        {
                //从终端输入要发送的消息
                fgets(buf, sizeof(buf), stdin);
                buf[strlen(buf)-1] = 0;

                //判断输入内容
                if(strcmp(buf, "quit")==0)
                {
                        break;
                }

                //将消息发送给服务器
                write(cfd, buf, strlen(buf));
                printf("发送成功\n");

                //接受服务器发来的消息
                bzero(buf, sizeof(buf));
                int res = read(cfd, buf, sizeof(buf));
                if(res == 0)
                {
                        printf("服务器已经下线\n");
                        break;
                }
                printf("收到服务器消息:%s\n", buf);

        }
        //5、关闭套接字
        close(cfd);

        return 0;
}

运行

UDP服务器和客户端通讯

服务器代码

#include<myhead.h>
#define SER_IP "192.168.109.12"
#define SER_PORT 8888


/*****************主程序*****************/
int main(int argc, const char *argv[])
{
        //1、创建一个用于通信的套接字文件描述符
        int sfd = socket(AF_INET, SOCK_DGRAM, 0);
        if(sfd == -1)
        {
                perror("socket error");
                return -1;
        }

        //2、绑定ip地址和端口号(必须)
        //2.1 封装结构体
        struct sockaddr_in sin;
        sin.sin_family = AF_INET;
        sin.sin_addr.s_addr = inet_addr(SER_IP);
        sin.sin_port = htons(SER_PORT);
        //2.2 绑定
        if(bind(sfd, (struct sockaddr*)&sin, sizeof(sin))==-1)
        {
                perror("bind error");
                return -1;
        }


        //3、数据收发
        char buf[128] = "";      //用于接受对端消息
        //定义一个地址信息结构体的变量,用于接收对端地址
        struct sockaddr_in cin;
        socklen_t addrlen = sizeof(cin);   //接受地址长度

        while(1)
        {
                //清空容器
                bzero(buf, sizeof(buf));

                //从套接字文件描述符中读取消息
                recvfrom(sfd, buf, sizeof(buf), 0, (struct sockaddr*)&cin, &addrlen);

                printf("[%s:%d] : %s\n",
                                inet_ntoa(cin.sin_addr), ntohs(cin.sin_port), buf);

                //给消息加个笑脸还回去
                strcat(buf, ":D");

                //发送消息
                sendto(sfd, buf, strlen(buf), 0, (struct sockaddr*)&cin, sizeof(cin));
                printf("发送成功\n");

        }

        //4、关闭套接字
        close(sfd);

        return 0;
}                            

客户端代码

#include<myhead.h>

#define SER_IP "192.168.109.12"
#define SER_PORT 8888


/******************主程序******************/
int main(int argc, const char *argv[])
{
        //1、创建一个用于通信的套接字文件描述符
        int cfd = socket(AF_INET, SOCK_DGRAM, 0);
        if(cfd == -1)
        {
                perror("socket error");
                return -1;
        }


        //2、绑定ip和端口号(可选)

        //3、数据收发
        char buf[128] = "";    //数据容器
        struct sockaddr_in sin;     //目标地址
        sin.sin_family = AF_INET;
        sin.sin_port = htons(SER_PORT);
        sin.sin_addr.s_addr = inet_addr(SER_IP);
        socklen_t addrlen = sizeof(sin);

        while(1)
        {
                //清空容器
                bzero(buf, sizeof(buf));
                fgets(buf, sizeof(buf), stdin);   //从终端获取数据
                buf[strlen(buf)-1] = 0;

                if(strcmp(buf,"quit")==0)
                {
                        break;
                }

                //将数据发送给服务器
                sendto(cfd, buf, strlen(buf), 0, (struct sockaddr*)&sin, sizeof(sin));
                printf("发送成功\n");

                //接收服务器发来的消息
                bzero(buf, sizeof(buf));

                //recvfrom(cfd, buf, sizeof(buf), 0, (struct socket*)&sin, &addrlen);
                //recvfrom(cfd, buf, sizeof(buf), 0, NULL,NULL);
                read(cfd, buf, sizeof(buf));
                printf("收到服务器消息为:%s\n", buf);

        }

        //4、关闭套接字
        close(cfd);

        return 0;
}

运行情况

牛客


网站公告

今日签到

点亮在社区的每一天
去签到