如何进行网络编程和套接字操作?
网络编程是计算机编程中重要的领域之一,它使程序能够在网络上进行数据传输和通信。C语言是一种强大的编程语言,也可以用于网络编程。网络编程通常涉及套接字(Socket)操作,套接字是一种用于网络通信的抽象接口。本文将详细讨论如何进行C语言网络编程和套接字操作。
第一部分:网络编程基础
在开始学习C语言网络编程之前,首先需要理解一些基本的概念和术语。
1.1 IP地址和端口号
-
IP地址:IP地址是用于标识计算机或设备在网络上的唯一地址。IPv4和IPv6是两种常用的IP地址协议,它们用于不同的网络环境。IPv4地址通常表示为四个十进制数,如
192.168.1.1
,而IPv6地址更长,以冒号分隔,如2001:0db8:85a3:0000:0000:8a2e:0370:7334
。 -
端口号:端口号用于标识正在运行的应用程序或服务。它是一个16位的整数,范围从0到65535。常见的端口号已被分配给特定的应用程序,例如HTTP通常使用端口80,HTTPS使用端口443。
1.2 客户端和服务器
在网络编程中,有两个主要的角色:客户端和服务器。
-
客户端:客户端是发送请求并接收服务器响应的程序或设备。它通常主动发起连接,并向服务器请求数据或服务。
-
服务器:服务器是接受客户端请求并提供相应服务的程序或设备。它通常监听一个特定的端口,并等待客户端连接。
1.3 套接字(Socket)
套接字是网络编程中的核心概念。套接字允许程序通过网络进行通信,可以是TCP套接字或UDP套接字。
-
TCP套接字:TCP(传输控制协议)提供可靠的、面向连接的通信。TCP套接字用于建立可靠的双向通信通道,数据按顺序传输,且不丢失。
-
UDP套接字:UDP(用户数据报协议)提供不可靠的、面向数据包的通信。UDP套接字用于快速数据传输,但不能保证数据的顺序和可靠性。
第二部分:套接字编程步骤
进行网络编程和套接字操作通常涉及以下步骤:
2.1 包含头文件
要进行套接字编程,需要包含C语言的相关头文件。最常用的头文件是<sys/socket.h>
、<netinet/in.h>
和<arpa/inet.h>
。这些头文件包含了套接字函数和网络地址结构的定义。
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
2.2 创建套接字
创建套接字是网络编程的第一步。使用socket
函数来创建套接字,该函数的原型如下
int socket(int domain, int type, int protocol);
-
domain
参数指定套接字的协议族,常用的是AF_INET
(IPv4)和AF_INET6
(IPv6)。 -
type
参数指定套接字的类型,常用的有SOCK_STREAM
(用于TCP)和SOCK_DGRAM
(用于UDP)。 -
protocol
参数通常设置为0,以便根据domain
和type
自动选择协议。
以下是创建TCP套接字的示例:
int sockfd = socket(AF_INET, SOCK_STREAM, 0);
if (sockfd == -1) {perror("Socket creation failed");// 处理错误
}
2.3 定义服务器和客户端地址
在网络通信中,服务器和客户端都需要定义自己的地址信息。这些信息包括IP地址和端口号。
定义服务器地址
struct sockaddr_in server_addr;
server_addr.sin_family = AF_INET; // 使用IPv4
server_addr.sin_port = htons(PORT_NUMBER); // 设置端口号(需要使用htons函数进行字节序转换)
server_addr.sin_addr.s_addr = INADDR_ANY; // 监听所有可用的网络接口
定义客户端地址
struct sockaddr_in client_addr;
client_addr.sin_family = AF_INET; // 使用IPv4
client_addr.sin_port = htons(PORT_NUMBER); // 设置服务器端口号
client_addr.sin_addr.s_addr = inet_addr(SERVER_IP); // 设置服务器IP地址
2.4 绑定套接字(服务器端)
在服务器端,需要将套接字绑定到一个特定的IP地址和端口号上,以便监听客户端连接。使用bind
函数来执行绑定操作:
int bind(int sockfd, const struct sockaddr *addr, socklen_t addrlen);
-
sockfd
是套接字描述符,即要绑定的套接字。 -
addr
是一个指向sockaddr
结构的指针,其中包含要绑定的地址信息。 -
addrlen
是addr
结构的长度。
以下是服务器端绑定套接字的示例:
if (bind(sockfd, (struct sockaddr *)&server_addr, sizeof(server_addr)) == -1) {perror("Bind failed");// 处理错误
}
2.5 监听连接请求(服务器端)
在服务器端,需要使用listen
函数开始监听客户端的连接请求:
int listen(int sockfd, int backlog);
-
sockfd
是套接字描述符,即要监听的套接字。 -
backlog
是等待连接队列的最大长度,通常设置为5或更大。
以下是服务器端监听连接请求的示例:
if (listen(sockfd, 5) == -1) {perror("Listen failed");// 处理错误
}
2.6 接受连接(服务器端)
当客户端尝试连接到服务器时,服务器需要使用accept
函数接受连接请求并创建新的套接字用于通信:
int new_socket = accept(int sockfd, struct sockaddr *addr, socklen_t *addrlen);
-
sockfd
是监听套接字的描述符。 -
addr
是一个指向sockaddr
结构的指针,用于存储客户端的地址信息。 -
addrlen
是addr
结构的长度。
accept
函数将返回一个新的套接字描述符,用于与客户端通信。服务器可以使用此套接字与客户端进行数据交换。
以下是服务器端接受连接的示例:
int new_socket;
socklen_t addr_len = sizeof(client_addr);
new_socket = accept(sockfd, (struct sockaddr *)&client_addr, &addr_len);
if (new_socket == -1) {perror("Accept failed");// 处理错误
}
2.7 连接到服务器(客户端)
在客户端,需要使用connect
函数连接到服务器:
int connect(int sockfd, const struct sockaddr *addr, socklen_t addrlen);
-
sockfd
是客户端套接字的描述符。 -
addr
是一个指向服务器地址的指针。 -
addrlen
是服务器地址结构的长度。
以下是客户端连接到服务器的示例:
if (connect(sockfd, (struct sockaddr *)&server_addr, sizeof(server_addr)) == -1) {perror("Connection failed");// 处理错误
}
2.8 发送和接收数据
一旦连接建立,服务器和客户端可以使用send
和recv
函数来发送和接收数据。
发送数据
ssize_t send(int sockfd, const void *buf, size_t len, int flags);
-
sockfd
是套接字描述符。 -
buf
是包含要发送数据的缓冲区的指针。 -
len
是要发送的数据的字节数。 -
flags
通常设置为0。
以下是发送数据的示例:
char message[] = "Hello, Server!";
send(new_socket, message, strlen(message), 0);
接收数据
ssize_t recv(int sockfd, void *buf, size_t len, int flags);
-
sockfd
是套接字描述符。 -
buf
是用于存储接收数据的缓冲区的指针。 -
len
是缓冲区的大小,表示最多可以接收多少字节的数据。 -
flags
通常设置为0。
以下是接收数据的示例:
char buffer[1024];
ssize_t bytes_received = recv(new_socket, buffer, sizeof(buffer), 0);
if (bytes_received == -1) {perror("Receive failed");// 处理错误
} else {buffer[bytes_received] = '\0'; // 添加字符串结束符printf("Received: %s\n", buffer);
}
2.9 关闭套接字
在完成通信后,服务器和客户端应使用close
函数关闭套接字以释放资源:
int close(int sockfd);
sockfd
是要关闭的套接字描述符。
以下是关闭套接字的示例:
close(new_socket); // 关闭与客户端的套接字
close(sockfd); // 关闭服务器监听套接字
第三部分:完整的示例
以下是一个简单的C语言网络编程示例,其中包括了创建服务器和客户端的代码。
服务器端示例
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>#define PORT_NUMBER 8080int main() {int sockfd, new_socket;struct sockaddr_in server_addr, client_addr;socklen_t addr_len = sizeof(client_addr);// 创建套接字sockfd = socket(AF_INET, SOCK_STREAM, 0);if (sockfd == -1) {perror("Socket creation failed");exit(1);}// 定义服务器地址server_addr.sin_family = AF_INET;server_addr.sin_port = htons(PORT_NUMBER);server_addr.sin_addr.s_addr = INADDR_ANY;// 绑定套接字到地址if (bind(sockfd, (struct sockaddr *)&server_addr, sizeof(server_addr)) == -1) {perror("Bind failed");exit(1);}// 监听连接请求if (listen(sockfd, 5) == -1) {perror("Listen failed");exit(1);}// 接受连接new_socket = accept(sockfd, (struct sockaddr *)&client_addr, &addr_len);if (new_socket == -1) {perror("Accept failed");exit(1);}// 接收数据char buffer[1024];ssize_t bytes_received = recv(new_socket, buffer, sizeof(buffer), 0);if (bytes_received == -1) {perror("Receive failed");exit(1);}buffer[bytes_received] = '\0'; // 添加字符串结束符printf("Received: %s\n", buffer);// 发送响应const char *response = "Hello, Client!";send(new_socket, response, strlen(response), 0);// 关闭套接字close(new_socket);close(sockfd);return 0;
}
客户端示例
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>#define SERVER_IP "127.0.0.1"
#define PORT_NUMBER 8080int main() {int sockfd;struct sockaddr_in server_addr;// 创建套接字sockfd = socket(AF_INET, SOCK_STREAM, 0);if (sockfd == -1) {perror("Socket creation failed");exit(1);}// 定义服务器地址server_addr.sin_family = AF_INET;server_addr.sin_port = htons(PORT_NUMBER);server_addr.sin_addr.s_addr = inet_addr(SERVER_IP);// 连接到服务器if (connect(sockfd, (struct sockaddr *)&server_addr, sizeof(server_addr)) == -1) {perror("Connection failed");exit(1);}// 发送数据const char *message = "Hello, Server!";send(sockfd, message, strlen(message), 0);// 接收响应char buffer[1024];ssize_t bytes_received = recv(sockfd, buffer, sizeof(buffer), 0);if (bytes_received == -1) {perror("Receive failed");exit(1);}buffer[bytes_received] = '\0'; // 添加字符串结束符printf("Received: %s\n", buffer);// 关闭套接字close(sockfd);return 0;
}
第四部分:网络编程进阶
以上示例介绍了基本的套接字编程步骤,但网络编程还涉及到更多高级概念和技术,例如多线程服务器、非阻塞套接字、套接字选项、数据序列化和安全性等。要深入学习网络编程,建议查阅相关文档和书籍,并尝试构建更复杂的网络应用程序。
此外,网络编程也需要考虑安全性和性能方面的问题。在实际应用中,您需要谨慎处理输入数据,防止网络攻击,并优化网络通信以提高性能。
总之,C语言网络编程是一个广阔而有趣的领域,它允许您构建各种网络应用程序,从简单的聊天客户端到复杂的服务器应用程序。通过深入学习套接字编程和网络协议,您将能够更好地理解和掌握网络编程的原理和实践。
相关文章:
如何进行网络编程和套接字操作?
网络编程是计算机编程中重要的领域之一,它使程序能够在网络上进行数据传输和通信。C语言是一种强大的编程语言,也可以用于网络编程。网络编程通常涉及套接字(Socket)操作,套接字是一种用于网络通信的抽象接口。本文将详…...
在Spark中集成和使用Hudi
本文介绍了在Spark中集成和使用Hudi的功能。使用Spark数据源API(scala和python)和Spark SQL,插入、更新、删除和查询Hudi表的代码片段。 1.安装 Hudi适用于Spark-2.4.3+和Spark 3.x版本。 1.1 Spark 3支持矩阵 Hudi...
力扣第226翻转二叉数 c++三种方法 +注释
题目 226. 翻转二叉树 简单 给你一棵二叉树的根节点 root ,翻转这棵二叉树,并返回其根节点。 示例 1: 输入:root [4,2,7,1,3,6,9] 输出:[4,7,2,9,6,3,1]示例 2: 输入:root [2,1,3] 输出&am…...
React项目部署 - Nginx配置
写在前面:博主是一只经过实战开发历练后投身培训事业的“小山猪”,昵称取自动画片《狮子王》中的“彭彭”,总是以乐观、积极的心态对待周边的事物。本人的技术路线从Java全栈工程师一路奔向大数据开发、数据挖掘领域,如今终有小成…...
【Vue3】定义全局变量和全局函数
// main.ts import { createApp } from vue import App from ./App.vue const app createApp(App)// 解决 ts 报错 type Filter {format<T>(str: T): string } declare module vue {export interface ComponentCustomProperties {$filters: Filter,$myArgs: string} }a…...
【Pandas】Apply自定义行数
文章目录 1. Series的apply方法2. DataFrame的apply方法2.1 针对列使用apply2.2 针对行使用apply Pandas提供了很多数据处理的API,但当提供的API不能满足需求的时候,需要自己编写数据处理函数, 这个时候可以使用apply函数apply函数可以接收一个自定义函数, 可以将DataFrame的行…...
C#,数值计算——完全VEGAS编码的蒙特·卡洛计算方法与源程序
1 文本格式 using System; namespace Legalsoft.Truffer { /// <summary> /// Complete VEGAS Code /// adaptive/recursive Monte Carlo /// </summary> public abstract class VEGAS { const int NDMX 50; const int …...
纯css实现3D鼠标跟随倾斜
老规矩先上图 为什么今天会想起来整这个呢?这是因为和我朋友吵架, 就是关于这个效果的,就是这个 卡片懸停毛玻璃效果, 我朋友认为纯css也能写, 我则坦言他就是在放狗屁,这种跟随鼠标的3D效果要怎么可能能用纯css写, 然后吵着吵着发现,欸,好像真能用css写哦,我以前还写过这种…...
Pandas数据结构
文章目录 1. Series数据结构1.1 Series数据类型创建1.2 Series的常用属性valuesindex/keys()shapeTloc/iloc 1.3 Series的常用方法mean()max()/min()var()/std()value_counts()describe() 1.4 Series运算加/减法乘法 2. DataFrame数据结构2.1 DataFrame数据类型创建2.2 布尔索引…...
systemverilog function的一点小case
关于function的应用无论是在systemverilog还是verilog中都有很广泛的应用,但是一直有一个模糊的概念困扰着我,今天刚好有时间来搞清楚并记录下来。 关于fucntion的返回值的问题: function integer clog2( input logic[255:0] value);for(cl…...
微服务的初步使用
环境说明 jdk1.8 maven3.6.3 mysql8 idea2022 spring cloud2022.0.8 微服务案例的搭建 新建父工程 打开IDEA,File->New ->Project,填写Name(工程名称)和Location(工程存储位置),选…...
【2023年11月第四版教材】第18章《项目绩效域》(合集篇)
第18章《项目绩效域》(合集篇) 1 章节内容2 干系人绩效域2.1 绩效要点2.2 执行效果检查2.3 与其他绩效域的相互作用 3 团队绩效域3.1 绩效要点3.2 与其他绩效域的相互作用3.3 执行效果检查3.4 开发方法和生命周期绩效域 4 绩效要点4.1 与其他绩效域的相互…...
Android 11.0 mt6771新增分区功能实现三
1.前言 在11.0的系统开发中,在对某些特殊模块中关于数据的存储方面等需要新增分区来保存, 所以就需要在系统分区新增分区,接下来就来实现这个功能,看系列三的实现过程 2.mt6771新增分区功能实现三的核心类 build/make/tools/releasetools/common.py device/mediatek/mt6…...
计算机网络——计算机网络的性能指标(上)-速率、带宽、吞吐量、时延
目录 速率 比特 速率 例1 带宽 带宽在模拟信号系统中的意义 带宽在计算机网络中的意义 吞吐量 时延 发送时延 传播时延 处理时延 例2 例3 速率 了解速率之前,先详细了解一下比特: 比特 计算机中数据量的单位,也是信息论中信…...
每日一题 518零钱兑换2(完全背包)
题目 给你一个整数数组 coins 表示不同面额的硬币,另给一个整数 amount 表示总金额。 请你计算并返回可以凑成总金额的硬币组合数。如果任何硬币组合都无法凑出总金额,返回 0 。 假设每一种面额的硬币有无限个。 题目数据保证结果符合 32 位带符号整…...
Linux shell编程学习笔记8:使用字符串
一、前言 字符串是大多数编程语言中最常用最有用的数据类型,这在Linux shell编程中也不例外。 本文讨论了Linux Shell编程中的字符串的三种定义方式的差别,以及字符串拼接、取字符串长度、提取字符串、查找子字符串等常用字符串操作,,以及反…...
【Spring笔记03】Spring依赖注入各种数据类型
这篇文章,详细介绍一下Spring框架中如何注入各种数据类型,包含:注入基本数据类型、数组、集合、Map映射、Property属性、注入空字符串、注入null值、注入特殊字符等内容,以及如何使用命名空间进行依赖注入。 目录 一、注入各种数据…...
2023计算机保研——双非上岸酒吧舞
我大概是从22年10月份开始写博客的,当时因为本校专业的培养方案的原因,课程很多,有些知识纸质记录很不方便,于是选择了打破了自己的成见使用博客来记录学习生活。对于我个人而言,保研生活在前一大半过程中都比较艰难&a…...
《计算机视觉中的多视图几何》笔记(13)
13 Scene planes and homographies 本章主要讲述两个摄像机和一个世界平面之间的射影几何关系。 我们假设空间有一平面 π \pi π,平面上的一点为 x π x_{\pi} xπ。 x π x_{\pi} xπ分别在两幅图像 P , P ′ P, P P,P′上形成了 x , x ′ x, x x,x′。 那…...
H5移动端购物商城系统源码 小型商城全新简洁风格全新UI 支持易支付接口
一款比较简单的 H5 移动端购物商城系统源码,比较适合单品商城、小型商城使用。带有易支付接口。 源码下载:https://download.csdn.net/download/m0_66047725/88391704 源码下载2:评论留言或私信留言...
全志ARM926 Melis2.0系统的开发指引⑤
全志ARM926 Melis2.0系统的开发指引⑤ 编写目的8. 固件修改工具(ImageModify)使用8.1.界面说明8.2.操作步骤8.2.1. 配置平台8.2.2. 选择固件8.2.3. 选择要替换的文件8.2.4. 替换文件8.2.5. 保存固件 8.3.注意事项8.4.增加固件修改权限设置8.4.1. 概述8.4.2. 操作说明8.4.2.1.打…...
【AI视野·今日Robot 机器人论文速览 第四十七期】Wed, 4 Oct 2023
AI视野今日CS.Robotics 机器人学论文速览 Wed, 4 Oct 2023 Totally 40 papers 👉上期速览✈更多精彩请移步主页 Interesting: 📚基于神经网络的多模态触觉感知, classification, position, posture, and force of the grasped object多模态形象的解耦(f…...
GPX可视化工具 GPX航迹预览工具
背景 当我们收到别人分享的航迹文档,即gpx文档时,如何快速的进行浏览呢?我们可以使用GIS软件来打开gpx文档并显示gpx中所记录的航迹,例如常用的GIS软件有googleEarth, Basecamp, GPXsee, GPX E…...
学信息系统项目管理师第4版系列18_采购管理
1. 协议 1.1. 合同 1.1.1. 国际合作的项目经理应牢记,无论合同规定如何详尽,文化和当地法律对合同及其可执行性均有影响 1.2. 服务水平协议(SLA) 1.3. 谅解备忘录 1.4. 协议备忘录(MOA) 1.5. 订购单 …...
标准化数据模型
标准化数据模型 标准化被定义为减少或消除数据集中冗余的过程。 它已成为关系数据库中数据建模的事实上的方法,很大程度上是由于这些系统最初设计时所围绕的底层资源限制:缓慢的磁盘和昂贵的 RAM。更少的数据冗余/重复意味着更有效地从磁盘读取数据并占…...
linux平台源码编译ffmpeg
目录 编译平台 编译步骤 编译平台 中标麒麟 编译步骤 1 从Download FFmpeg 下载源码,我选中了4.2.9版 2 解压 3 在解压后的目录下输入 ./configure --enable-shared --prefix/usr/local/ffmpeg 4 make 5 sudo make install 6 ffmpeg的头文件、可执行程…...
Vue中如何进行拖拽与排序功能实现
在Vue中实现拖拽与排序功能 在Web应用程序中,实现拖拽和排序功能是非常常见的需求,特别是在管理界面、任务列表和图形用户界面等方面。Vue.js作为一个流行的JavaScript框架,提供了许多工具和库来简化拖拽和排序功能的实现。本文将介绍如何使…...
新款UI动态壁纸头像潮图小程序源码
新款UI动态壁纸头像潮图小程序源码,不需要域名服务器,直接添加合法域名,上传发布就能使用。 可以对接开通流量主,个人也能运营,不需要服务器源码完整。整合头像,动态壁纸,文案功能齐全。 源码…...
Python逐日填补Excel中的日期并用0值填充缺失日期的数据
本文介绍基于Python语言,读取一个不同的列表示不同的日期的.csv格式文件,将其中缺失的日期数值加以填补;并用0值对这些缺失日期对应的数据加以填充的方法。 首先,我们明确一下本文的需求。现在有一个.csv格式文件,其第…...
【C语言经典100例题-70】求一个字符串的长度(指针)
代码 使用指针来遍历字符串,直到遇到字符串结尾的空字符\0为止,统计字符数量即为字符串长度。 #include<stdio.h> #define n 20 int getlength(char *a) {int len 0;while(*a!\0){len;a;}return len; } int main() {char *arr[n] { 0 };int l…...
网站建设培训南宁/上海搜索引擎优化1
内容:1、rsyslog日志服务简介2、rsyslog的配置详解3、实现日志服务器收集日志及last、lastb、dmseg命令的使用4、实现日志存储在mysql中一、rsyslog日志服务简介日志的概念好理解,日志作用可用于排障和追溯审计的等1、rsyslog是一个C/S架构的服务&#x…...
个人网站可以做品牌推广/手机助手
题目:第一步创建对象:1. 表1, 表名:T_USER (系统用户)字段名类型 是否可为空长度IDNUMBER不可3NAMEVARCHAR2不可32个字符TYPEchar不可 1个字符MOBILENOVARCHAR2可以11个字符CREATED_TIMEDATE不可…...
重庆网站建设的价格低/郴州网站建设网络推广渠道
1、有两根不均匀分布的香,香烧完的时间是一个小时,你能用什么方法来确定一段15分钟的时间? 2、一个经理有三个女儿,三个女儿的年龄加起来等于13,三个女儿的年龄乘起来等于经理自己的年龄,有一个下属已知道…...
网站建设安全性/武汉seo学徒
本人从两个方面去解释如何进行redis性能优化,经验是很根据线上环境的使用总结的。欢迎咨询QQ 2767855941 1 连接数优化 redis使用的IO多路复用技术,关于redis IO多路复用技术就不在此具体说明,只能说由于redis使用了这个技术,导致…...
wordpress怎么开启注册/sem 优化软件
DevExtreme拥有高性能的HTML5 / JavaScript小部件集合,使您可以利用现代Web开发堆栈(包括React,Angular,ASP.NET Core,jQuery,Knockout等)构建交互式的Web应用程序。从Angular和Reac,…...
wordpress 博客系统/网络宣传推广
今天在手机UC上发现我的一个网页打不开,而在PC上是正常的,因此需要通过Chrome远程调试手机端UC浏览器查下问题,折腾了老久才弄好。 获取 Google USB 驱动程序 首先将手机通过USB接口与PC连接接着要确认手机USB驱动程序是不是正常,…...