Socket 函数详细讲解(Socket编程步骤、socket函数、TCP和UDP的区别)
Socket 函数详细讲解和 C++ 示例
- 一、 Socket 基本概念
- 1. Socket 简介
- 2. Socket 编程步骤
- 3. TCP Socket 编程示例
- 服务器端
- 客户端
- 4. 详细说明
- 二、 socket 函数
- 1. domain 通讯的协议家族
- 2. type 数据传输的类型
- 3. protocol 最终使用的协议
- 返回值
- 示例
- 三、TCP 和 UDP的区别
- 1. TCP(传输控制协议)
- 2. UDP(用户数据报协议)
- 3. 总结
- 示例应用
一、 Socket 基本概念
1. Socket 简介
Socket 是一种通信机制,允许在不同主机之间或同一主机的不同进程之间进行数据交换。使用 socket 编程可以实现 TCP 和 UDP 协议的网络通信。
2. Socket 编程步骤
- 创建 Socket
- 绑定(仅服务器)
- 监听(仅服务器)
- 接受连接(仅服务器)
- 连接服务器(仅客户端)
- 发送和接收数据
- 关闭 Socket
3. TCP Socket 编程示例
服务器端
#include <iostream>
#include <cstring>
#include <unistd.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>#define PORT 8080
#define BUFFER_SIZE 1024int main() {int server_fd, new_socket;struct sockaddr_in address;int addrlen = sizeof(address);char buffer[BUFFER_SIZE] = {0};// 创建 socket 文件描述符if ((server_fd = socket(AF_INET, SOCK_STREAM, 0)) == 0) {perror("socket failed");exit(EXIT_FAILURE);}// 绑定address.sin_family = AF_INET;address.sin_addr.s_addr = INADDR_ANY;address.sin_port = htons(PORT);if (bind(server_fd, (struct sockaddr *)&address, sizeof(address)) < 0) {perror("bind failed");close(server_fd);exit(EXIT_FAILURE);}// 监听if (listen(server_fd, 3) < 0) {perror("listen failed");close(server_fd);exit(EXIT_FAILURE);}// 接受连接if ((new_socket = accept(server_fd, (struct sockaddr *)&address, (socklen_t*)&addrlen)) < 0) {perror("accept failed");close(server_fd);exit(EXIT_FAILURE);}// 读取客户端发送的数据read(new_socket, buffer, BUFFER_SIZE);std::cout << "Message from client: " << buffer << std::endl;// 发送数据给客户端const char *message = "Hello from server";send(new_socket, message, strlen(message), 0);std::cout << "Hello message sent\n";// 关闭 socketclose(new_socket);close(server_fd);return 0;
}
客户端
#include <iostream>
#include <cstring>
#include <unistd.h>
#include <arpa/inet.h>#define PORT 8080
#define BUFFER_SIZE 1024int main() {int sock = 0;struct sockaddr_in serv_addr;char buffer[BUFFER_SIZE] = {0};// 创建 socket 文件描述符if ((sock = socket(AF_INET, SOCK_STREAM, 0)) < 0) {std::cerr << "Socket creation error" << std::endl;return -1;}serv_addr.sin_family = AF_INET;serv_addr.sin_port = htons(PORT);// 将地址转换成二进制if (inet_pton(AF_INET, "127.0.0.1", &serv_addr.sin_addr) <= 0) {std::cerr << "Invalid address/ Address not supported" << std::endl;return -1;}// 连接服务器if (connect(sock, (struct sockaddr *)&serv_addr, sizeof(serv_addr)) < 0) {std::cerr << "Connection Failed" << std::endl;return -1;}// 发送数据给服务器const char *message = "Hello from client";send(sock, message, strlen(message), 0);std::cout << "Hello message sent\n";// 读取服务器发送的数据read(sock, buffer, BUFFER_SIZE);std::cout << "Message from server: " << buffer << std::endl;// 关闭 socketclose(sock);return 0;
}
4. 详细说明
-
创建 Socket
socket(int domain, int type, int protocol)
domain
: 使用的协议族,例如AF_INET
表示 IPv4 网络协议。type
: Socket 类型,例如SOCK_STREAM
表示面向连接的 TCP。protocol
: 一般设置为 0,让系统自动选择合适的协议。
-
绑定
bind(int sockfd, const struct sockaddr *addr, socklen_t addrlen)
- 将 socket 绑定到特定的 IP 地址和端口号。
-
监听
listen(int sockfd, int backlog)
- 使 socket 处于监听状态,准备接受连接。
backlog
指定等待连接队列的最大长度。
-
接受连接
accept(int sockfd, struct sockaddr *addr, socklen_t *addrlen)
- 从监听队列中接受一个连接,返回一个新的 socket 文件描述符,用于与客户端通信。
-
连接服务器
connect(int sockfd, const struct sockaddr *addr, socklen_t addrlen)
- 客户端使用这个函数连接到服务器。
-
发送和接收数据
send(int sockfd, const void *buf, size_t len, int flags)
recv(int sockfd, void *buf, size_t len, int flags)
read
和write
也可以用于接收和发送数据。
-
关闭 Socket
close(int sockfd)
- 关闭 socket 文件描述符。
二、 socket 函数
socket(int domain, int type, int protocol)
domain
: 使用的协议族,例如AF_INET
表示 IPv4 网络协议。type
: Socket 类型,例如SOCK_STREAM
表示面向连接的 TCP。protocol
: 一般设置为 0,让系统自动选择合适的协议。
1. domain 通讯的协议家族
- PF_INET IPv4互联网协议族。
- PF_INET6 IPv6互联网协议族。
- PF_LOCAL 本地通信的协议族。
- PF_PACKET 内核底层的协议族。
- PF_IPX IPX Novell协议族。
IPv6尚未普及,其它的不常用。
2. type 数据传输的类型
- SOCK_STREAM 面向连接的socket:
-----1)数据不会丢失;2)数据的顺序不会错乱;3)双向通道。 - SOCK_DGRAM 无连接的socket:
-----1)数据可能会丢失;2)数据的顺序可能会错乱;3)传输的效率更高。
3. protocol 最终使用的协议
protocol:协议类型
- 通常为
0
,表示自动选择与指定域和类型匹配的协议。 - 对于
AF_INET
和SOCK_STREAM
,默认为IPPROTO_TCP
。 - 对于
AF_INET
和SOCK_DGRAM
,默认为IPPROTO_UDP
。
返回值
- 成功时返回一个新的套接字描述符。
- 失败时返回
-1
,并设置errno
以指示错误类型。
示例
int sockfd = socket(AF_INET, SOCK_STREAM, 0);
if (sockfd == -1) {perror("socket failed");exit(EXIT_FAILURE);
}
在IPv4网络协议家族中,数据传输方式为SOCK_STREAM
的协议只有IPPROTO_TCP
,数据传输方式为SOCK_DGRAM
的协议只有IPPROTO_UDP
。
本参数也可以为0
socket(PF_INET, SOCK_STREAM, IPPROTO_TCP); // 创建tcp的sock
socket(PF_INET, SOCK_DGRAM, IPPROTO_UDP); // 创建udp的sock
三、TCP 和 UDP的区别
TCP(传输控制协议)和UDP(用户数据报协议)是两种主要的传输层协议,用于网络通信。它们有各自的优缺点和适用场景。
1. TCP(传输控制协议)
-
连接导向:
- TCP是面向连接的协议,在传输数据之前需要建立连接(三次握手)。
- 连接建立后,双方可以进行可靠的数据传输。
-
可靠性:
- 提供可靠的数据传输,确保数据包按顺序到达并且没有丢失或重复。
- 使用确认机制、重传机制和校验和来保证数据的完整性和正确性。
-
流量控制:
- 具有流量控制和拥塞控制机制,防止网络拥塞和发送方发送速度过快。
- 使用滑动窗口协议来管理流量控制。
-
传输速度:
- 由于其可靠性和流量控制机制,TCP的传输速度相对较慢,但可靠性高。
-
头部开销:
- TCP头部较大,通常为20字节(不包括可选字段)。
-
适用场景:
- 适用于需要高可靠性的数据传输场景,如网页浏览(HTTP/HTTPS)、文件传输(FTP)、电子邮件(SMTP)、远程登录(SSH)等。
2. UDP(用户数据报协议)
-
无连接:
- UDP是无连接的协议,在传输数据之前不需要建立连接。
- 数据包独立发送,无需维护连接状态。
-
不可靠性:
- 提供不可靠的数据传输,不保证数据包的顺序、无丢失和无重复。
- 发送数据后不确认是否到达目的地,不重传丢失的数据包。
-
无流量控制:
- UDP没有流量控制和拥塞控制机制,发送速度完全取决于应用程序。
-
传输速度:
- 由于没有连接建立、流量控制和重传机制,UDP的传输速度较快,但可靠性低。
-
头部开销:
- UDP头部较小,固定为8字节。
-
适用场景:
- 适用于对传输速度要求高但对可靠性要求不高的场景,如视频直播、在线游戏、实时语音通话(VoIP)、广播通信等。
3. 总结
特性 | TCP | UDP |
---|---|---|
连接性 | 面向连接(需要三次握手) | 无连接 |
可靠性 | 可靠传输,保证顺序和完整性 | 不可靠传输,不保证顺序和完整性 |
流量控制 | 有流量控制和拥塞控制 | 无流量控制和拥塞控制 |
传输速度 | 较慢 | 较快 |
头部开销 | 较大(20字节,不包括可选字段) | 较小(8字节) |
适用场景 | 需要高可靠性的应用 | 需要高速度的应用 |
示例应用
- TCP:HTTP/HTTPS、FTP、SMTP、SSH、Telnet
- UDP:DNS查询、DHCP、TFTP、在线游戏、视频流、实时音频
了解TCP和UDP的区别及其适用场景,可以帮助开发人员在实际网络编程中选择合适的传输层协议,以满足不同应用的需求。
相关文章:
Socket 函数详细讲解(Socket编程步骤、socket函数、TCP和UDP的区别)
Socket 函数详细讲解和 C 示例 一、 Socket 基本概念1. Socket 简介2. Socket 编程步骤3. TCP Socket 编程示例服务器端客户端 4. 详细说明 二、 socket 函数1. domain 通讯的协议家族2. type 数据传输的类型3. protocol 最终使用的协议返回值示例 三、TCP 和 UDP的区别1. TCP&…...

【限免】杂波环境下线性调频脉冲、巴克码、频率步进脉冲雷达MTI、脉冲压缩【附MATLAB代码】
来源:微信公众号:EW Frontier 本代码主要模拟杂波环境(飞机、地杂波、鸟类信号)下,Chirp脉冲、巴克码脉冲、频率步进脉冲雷达信号的脉冲压缩及MTI、匹配滤波。 MATLAB主代码 % 定义参数 fs 1000; % 采样率 T 1; …...
前端最新面试题(Javascript模块篇)
目录 1 数据类型基础 1.1 JS内置类型 1.2 null和undefined区别 1.3 null是对象吗?为什么? 1.4 1.toString()为什么可以调用? 1.5 0.1+0.2为什么不等于0.3?如何让其相等 1.6 如何理解BigInt 1.7 JS 整数是怎么表示的 1.8 Number() 的存储空间是多大?如果后台发送了…...

Android11热点启动和关闭
Android官方关于Wi-Fi Hotspot (Soft AP) 的文章:https://source.android.com/docs/core/connect/wifi-softap?hlzh-cn 在 Android 11 的WifiManager类中有一套系统 API 可以控制热点的开和关,代码如下: 开启热点: // SoftApC…...

DI-engine强化学习入门(三)DI-ZOO强化学习环境搭建与示例运行——Atari
Atari是一家知名的电子游戏公司,成立于1972年,是早期电子游戏产业的先驱之一。在强化学习领域,提到Atari通常指的是Atari 2600游戏的一系列环境,这些环境是用于开发和测试强化学习算法的标准平台。 Atari 2600 强化学习环境概述 …...
【一站式学会Kotlin】第十节:kotlin 语言的可控性特点和安全调用操作符
作者介绍: 百度资深Android工程师T6,在百度任职7年半。 目前:成立赵小灰代码工作室,欢迎大家找我交流Android、微信小程序、鸿蒙项目。= 一:通俗易懂的人工智能教程:https://www.captainbed.cn/nefu/ 点一下,打开新世界的大门。 二:【一站式学会Kotlin】免费领取:作者…...
PaddleClas 指定gpu
在使用PaddleClas进行模型训练或预测时,如果您想要指定使用特定的GPU设备,可以通过CUDA_VISIBLE_DEVICES环境变量来设置。 在命令行中设置GPU的方法如下: # 指定第0号GPU export CUDA_VISIBLE_DEVICES0 # 之后运行PaddleClas的命令…...

langchain进阶一:特殊的chain,轻松实现对话,与数据库操作,抽取数据,以及基于本地知识库的问答
特殊的chain langchain中的Chain有很多,能够轻松实现部分需求,极致简化代码,但是实现效果与模型智慧程度有关 会话链 效果与LLMChain大致相同 javascript 复制代码 from langchain.chains import ConversationChain from langchain_community.llms import OpenAI conversat…...

【Spring Boot】响应式编程
响应式编程 1.WebFlux2.比较 MVC 和 WebFlux2.1 工作方式2.2 Spring MVC 与 Spring WebFlux 的区别2.3 使用 WebFlux 的好处 3.Mono 和 Flux3.1 Mono 和 Flux 是什么3.2 Mono 和 Flux 的区别 4.开发 WebFlux 的流程4.1 注解式开发流程4.2 响应式开发流程 5.用注解式开发实现 He…...

【C++练级之路】【Lv.21】C++11——列表初始化和声明
快乐的流畅:个人主页 个人专栏:《算法神殿》《数据结构世界》《进击的C》 远方有一堆篝火,在为久候之人燃烧! 文章目录 引言一、列表初始化1.1 内置类型1.2 结构体或类1.3 容器 二、声明2.1 auto2.2 decltype2.3 nullptr 三、STL的…...

输入一串字符串,前中后都有*号,去掉字符串中间和后面的*号,保留前面的*号和字母
#include <stdio.h> void fun(char* a) {//***df**fr*fg***int i 0, j 0,n0,m0;char* p;p a;while (p[i] ! \0){i;//i是一共的字符的个数}printf("%d\n",i);while (a[n] *){n;//计算字母前的*的个数}printf("%d\n", n);m n;for (j n; j < …...

【机器学习与大模型】驱动下的应用图像识别与处理
摘要: 本文深入探讨了机器学习在图像识别与处理领域的应用,特别是在大模型的推动下所取得的巨大进展。详细阐述了图像识别与处理的基本原理、关键技术,以及机器学习算法和大模型如何提升其性能和准确性。通过实际案例分析了其在多个领域的广泛…...

24李林跌落神坛,880还刷吗?还是换1000、900、660?
“李林今年跌落神坛了!” “全是固定题型没新题,结果今年考的全是新题。” 880是“老真题的神”, 遇到24年,冷门考点多,计算量又大,就不灵了。 但“老真题”,还是得刷。就像往年真题是要刷的…...
数据库漫谈-sybase
sybase就是“system”加“database”,代表着信息系统的底层。Sybase公司很早就推出了关系数据库产品(1987年5月推出的Sybase SQLServer1.0)。Sybase也是第一个提出Client/Server 体系结构的思想,并率先在Sybase SQLServer 中实现。…...

Springboot开发 -- Postman 调试类型详解
引言 在 Spring Boot 应用开发过程中,接口测试是必不可少的一环。Postman 作为一款强大的 API 开发和测试工具,可以帮助开发者轻松构建、测试和管理 HTTP 请求。本文将为大家介绍如何在 Spring Boot 开发中使用 Postman 进行接口测试。 一、准备工作 安…...
Windows 后台启动jar并且输出日志到特定日志
Windows 后台启动jar并且输出日志到特定日志 javaw -Dfile.encodingutf-8 -jar xxx.jar >log.log 2>&1 &日志输出以年月日格式显示 javaw -Dfile.encodingutf-8 -jar xxx.jar >log_%DATE:~0,4%-%DATE:~5,2%-%DATE:~8,2%_%TIME:~0,2%-%TIME:~3,2%-%TIME:~6,2…...

垃圾回收机制及算法
文章目录 概要对象存活判断引用计数算法可达性分析算法对象是否存活各种引用 垃圾收集算法分代收集理论复制算法标记清除算法标记-整理算法 概要 垃圾收集(Garbage Collection, 下文简称GC),其优缺点如下: 优点&#…...
蓝桥杯-暴力搜索BFS+DFS
九九乘法表挂毯 问题描述: 在一个古老的城堡里,一位名为 Alex 的少年发现了一幅巨大的九九乘法表挂毯。挂毯被划分成了9x9的方格,每个方格上写着相应的乘积。Alex 想象自己站在数值为1的方格上,他的目标是到达数值为 81 的方格。…...
巧用count与count()
在C#中,talentInnoPfChains.Count() 和 talentInnoPfChains.Count 的性能差异主要取决于 talentInnoPfChains 的类型。这里有两种可能的情况: 如果 talentInnoPfChains 是一个实现了 ICollection<T> 接口的集合(如 List<T>, Hash…...
MongoDB 覆盖索引查询:提升性能的完整指南
MongoDB 覆盖索引查询是一种优化数据库查询性能的技术,它通过创建适当的索引,使查询可以直接从索引中获取所需的数据,而无需访问实际的文档数据。这种方式可以减少磁盘 I/O 和内存消耗,提高查询性能。 基本语法 在 MongoDB 中&a…...

eNSP-Cloud(实现本地电脑与eNSP内设备之间通信)
说明: 想象一下,你正在用eNSP搭建一个虚拟的网络世界,里面有虚拟的路由器、交换机、电脑(PC)等等。这些设备都在你的电脑里面“运行”,它们之间可以互相通信,就像一个封闭的小王国。 但是&#…...

《从零掌握MIPI CSI-2: 协议精解与FPGA摄像头开发实战》-- CSI-2 协议详细解析 (一)
CSI-2 协议详细解析 (一) 1. CSI-2层定义(CSI-2 Layer Definitions) 分层结构 :CSI-2协议分为6层: 物理层(PHY Layer) : 定义电气特性、时钟机制和传输介质(导线&#…...
TRS收益互换:跨境资本流动的金融创新工具与系统化解决方案
一、TRS收益互换的本质与业务逻辑 (一)概念解析 TRS(Total Return Swap)收益互换是一种金融衍生工具,指交易双方约定在未来一定期限内,基于特定资产或指数的表现进行现金流交换的协议。其核心特征包括&am…...

C# 类和继承(抽象类)
抽象类 抽象类是指设计为被继承的类。抽象类只能被用作其他类的基类。 不能创建抽象类的实例。抽象类使用abstract修饰符声明。 抽象类可以包含抽象成员或普通的非抽象成员。抽象类的成员可以是抽象成员和普通带 实现的成员的任意组合。抽象类自己可以派生自另一个抽象类。例…...
数据库分批入库
今天在工作中,遇到一个问题,就是分批查询的时候,由于批次过大导致出现了一些问题,一下是问题描述和解决方案: 示例: // 假设已有数据列表 dataList 和 PreparedStatement pstmt int batchSize 1000; // …...
【HTTP三个基础问题】
面试官您好!HTTP是超文本传输协议,是互联网上客户端和服务器之间传输超文本数据(比如文字、图片、音频、视频等)的核心协议,当前互联网应用最广泛的版本是HTTP1.1,它基于经典的C/S模型,也就是客…...

Android 之 kotlin 语言学习笔记三(Kotlin-Java 互操作)
参考官方文档:https://developer.android.google.cn/kotlin/interop?hlzh-cn 一、Java(供 Kotlin 使用) 1、不得使用硬关键字 不要使用 Kotlin 的任何硬关键字作为方法的名称 或字段。允许使用 Kotlin 的软关键字、修饰符关键字和特殊标识…...
Device Mapper 机制
Device Mapper 机制详解 Device Mapper(简称 DM)是 Linux 内核中的一套通用块设备映射框架,为 LVM、加密磁盘、RAID 等提供底层支持。本文将详细介绍 Device Mapper 的原理、实现、内核配置、常用工具、操作测试流程,并配以详细的…...

GitFlow 工作模式(详解)
今天再学项目的过程中遇到使用gitflow模式管理代码,因此进行学习并且发布关于gitflow的一些思考 Git与GitFlow模式 我们在写代码的时候通常会进行网上保存,无论是github还是gittee,都是一种基于git去保存代码的形式,这样保存代码…...

抽象类和接口(全)
一、抽象类 1.概念:如果⼀个类中没有包含⾜够的信息来描绘⼀个具体的对象,这样的类就是抽象类。 像是没有实际⼯作的⽅法,我们可以把它设计成⼀个抽象⽅法,包含抽象⽅法的类我们称为抽象类。 2.语法 在Java中,⼀个类如果被 abs…...