使用C语言设计基于UDP的简易聊天室代码
时间: 2023-09-13 07:05:41 浏览: 262
以下是使用C语言设计基于UDP的简易聊天室的代码示例:
服务器端代码:
```c
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/socket.h>
#include <arpa/inet.h>
#include <pthread.h>
#define BUF_SIZE 1024
// 客户端信息结构体
typedef struct {
struct sockaddr_in addr;
int connfd;
} client_info;
// 客户端信息列表
client_info *clients[10];
int num_clients = 0;
// UDP Socket对象和地址信息
int server_socket;
struct sockaddr_in server_addr;
// 发送数据的线程函数
void *send_data(void *arg) {
char buffer[BUF_SIZE];
while (1) {
// 从标准输入获取数据
fgets(buffer, BUF_SIZE, stdin);
// 将数据发送给所有客户端
for (int i = 0; i < num_clients; i++) {
sendto(server_socket, buffer, strlen(buffer), 0, (struct sockaddr *)&(clients[i]->addr), sizeof(clients[i]->addr));
}
}
return NULL;
}
// 接收数据的线程函数
void *recv_data(void *arg) {
char buffer[BUF_SIZE];
while (1) {
// 接收数据报
struct sockaddr_in client_addr;
socklen_t client_addr_len = sizeof(client_addr);
int n = recvfrom(server_socket, buffer, BUF_SIZE, 0, (struct sockaddr *)&client_addr, &client_addr_len);
if (n > 0) {
buffer[n] = '\0';
printf("%s:%d说:%s", inet_ntoa(client_addr.sin_addr), ntohs(client_addr.sin_port), buffer);
// 转发数据给所有客户端
for (int i = 0; i < num_clients; i++) {
if (memcmp(&client_addr, &clients[i]->addr, sizeof(client_addr)) != 0) {
sendto(server_socket, buffer, strlen(buffer), 0, (struct sockaddr *)&(clients[i]->addr), sizeof(clients[i]->addr));
}
}
}
}
return NULL;
}
int main(int argc, char *argv[]) {
// 创建UDP Socket对象
server_socket = socket(AF_INET, SOCK_DGRAM, 0);
if (server_socket < 0) {
perror("socket");
exit(EXIT_FAILURE);
}
// 设置地址信息
memset(&server_addr, 0, sizeof(server_addr));
server_addr.sin_family = AF_INET;
server_addr.sin_addr.s_addr = htonl(INADDR_ANY);
server_addr.sin_port = htons(8888);
// 绑定地址信息
if (bind(server_socket, (struct sockaddr *)&server_addr, sizeof(server_addr)) < 0) {
perror("bind");
exit(EXIT_FAILURE);
}
// 创建发送数据的线程
pthread_t send_thread;
if (pthread_create(&send_thread, NULL, send_data, NULL) != 0) {
perror("pthread_create");
exit(EXIT_FAILURE);
}
// 创建接收数据的线程
pthread_t recv_thread;
if (pthread_create(&recv_thread, NULL, recv_data, NULL) != 0) {
perror("pthread_create");
exit(EXIT_FAILURE);
}
// 接收客户端连接
while (1) {
struct sockaddr_in client_addr;
socklen_t client_addr_len = sizeof(client_addr);
char buffer[BUF_SIZE];
int n = recvfrom(server_socket, buffer, BUF_SIZE, 0, (struct sockaddr *)&client_addr, &client_addr_len);
if (n > 0) {
buffer[n] = '\0';
int already_connected = 0;
// 检查客户端是否已经连接
for (int i = 0; i < num_clients; i++) {
if (memcmp(&client_addr, &clients[i]->addr, sizeof(client_addr)) == 0) {
already_connected = 1;
break;
}
}
if (!already_connected) {
// 添加新的客户端信息到列表中
client_info *info = (client_info *)malloc(sizeof(client_info));
info->addr = client_addr;
info->connfd = server_socket;
clients[num_clients++] = info;
printf("%s:%d已连接\n", inet_ntoa(client_addr.sin_addr), ntohs(client_addr.sin_port));
}
}
}
return 0;
}
```
客户端代码:
```c
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/socket.h>
#include <arpa/inet.h>
#include <pthread.h>
#define BUF_SIZE 1024
// UDP Socket对象和地址信息
int client_socket;
struct sockaddr_in server_addr;
// 发送数据的线程函数
void *send_data(void *arg) {
char buffer[BUF_SIZE];
while (1) {
// 从标准输入获取数据
fgets(buffer, BUF_SIZE, stdin);
// 将数据发送到服务器
sendto(client_socket, buffer, strlen(buffer), 0, (struct sockaddr *)&server_addr, sizeof(server_addr));
}
return NULL;
}
// 接收数据的线程函数
void *recv_data(void *arg) {
char buffer[BUF_SIZE];
while (1) {
// 接收数据报
struct sockaddr_in server_addr;
socklen_t server_addr_len = sizeof(server_addr);
int n = recvfrom(client_socket, buffer, BUF_SIZE, 0, (struct sockaddr *)&server_addr, &server_addr_len);
if (n > 0) {
buffer[n] = '\0';
printf("%s:%d说:%s", inet_ntoa(server_addr.sin_addr), ntohs(server_addr.sin_port), buffer);
}
}
return NULL;
}
int main(int argc, char *argv[]) {
// 创建UDP Socket对象
client_socket = socket(AF_INET, SOCK_DGRAM, 0);
if (client_socket < 0) {
perror("socket");
exit(EXIT_FAILURE);
}
// 设置服务器地址信息
memset(&server_addr, 0, sizeof(server_addr));
server_addr.sin_family = AF_INET;
server_addr.sin_addr.s_addr = inet_addr("127.0.0.1");
server_addr.sin_port = htons(8888);
// 创建发送数据的线程
pthread_t send_thread;
if (pthread_create(&send_thread, NULL, send_data, NULL) != 0) {
perror("pthread_create");
exit(EXIT_FAILURE);
}
// 创建接收数据的线程
pthread_t recv_thread;
if (pthread_create(&recv_thread, NULL, recv_data, NULL) != 0) {
perror("pthread_create");
exit(EXIT_FAILURE);
}
// 等待线程结束
pthread_join(send_thread, NULL);
pthread_join(recv_thread, NULL);
return 0;
}
```
以上是使用C语言设计基于UDP的简易聊天室的代码示例,您可以根据需求进行相应的修改和完善。需要注意的是,这只是一个简单的示例,实际应用中还需要考虑一些其他的因素,比如数据的安全性、数据的可靠性等。
阅读全文