第三天:实现网络编程基于tcp/udp协议在Ubuntu与gec6818开发板之间双向通信

互联网地址

每一台设备接入互联网后,都会举报一个唯一的地址编号

IP地址 INTERNET地址

internet地址 :它是协议上的一个逻辑地址

目前来说,我们主要的IP地址有两类 IPV4 IPV6

IPV4 其实就是使用一个32bit整数作为IP

IPV6 其实就是使用一个128bit整数作为IP

ipv4

1010 1100 0000 0010 0000 0001 0000 0001 人类是看不到的

172.2.1.1 给人看的"点分式"

每8bit组成一个十进制数,以 ‘.’ 隔开

2^32 个地址

这么多地址,怎么去管理?

类似电话号码 =区号+主机号

+86 0731 12345678

+86 中国大陆

0731 长沙

12345678 具体那个电话的号码

同理,ip地址也分为两个部分

ip地址=网络号+主机号

网络号:用于标识网络中的某个子网,占ip地址中的高x位

主机号:用于标识同一个子网内的不同主机,占地址中低的(32-x)位

也叫做 子网号 子网主机号

所占的bit位x又怎么确定呢?

netmask 子网掩码,用来确定一个ip地址中,网络号与主机号的占比

IP地址的bit位在子网掩码中对应的bit为1,就是网络号

在子网掩码中为0,就是主机号

比如:

ip 172.2.1.1

netmask 255.255.255.0

网络号 ip&netmask 172.2.1.0

主机号的范围 172.2.1.0 ~ 172.2.1.255

目前ip地址主要分为5类

在这里插入图片描述

我们常用的是C类网络

端口号

在网络中,可以提供ip地址来区分不同的网络设备

如果两个设备的IP相同 —》ip冲突,只有一台能够接入网络

问题;一台设备上,或许会运行多个网络应用

比如:我打开QQ给你们传文件,同时还在直播上课

那么网络中,怎么知道传递的数据,是由哪个网络应用发起的呢?

ip只能区分是那一台主机,不能区分是那一个应用

为了区分哪个网络应用传输的数据,需要用到端口号

TCP和UDP都是采用16bit无符号整数来作为端口号标识网络应用

IP —>标识网络中的某个设备

端口 —》标识设备上的某个网络应用

一台主机上的网络应用由:

ip地址+传输层协议(TCP/UDP)+端口号来确定

端口号 由 IANS 来管理

1-1023 众所周知的端口

比如 HTTP应用 80

FTP服务 20

1024-49151 注册端口,提供注册端口

49151-65536 动态或者私有端口,可以随便用

字节序

大端模式

高地址存储低字节 低地址存储高字节

小端模式

低地址存储低字节 高地址存储高字节

比如: int a = 0x12345678

&a = 0x4000

内存地址大端模式存储内容小端模式存储内容
0x40000x120x78
0x40010x340x56
0x40020x560x34
0x40030x780x12

不同的系统对于内存的管理方法不同,可能采用大端模式,可能采用小端模式

练习:尝试写一个程序,判断自己的Linux系统是大端模式还是小端模式,并且输出结果

int a = 1; //0x00 00 00 01
char *p = &a
if(*p == 1)
{printf("小端模式\n");
}
else
{printf("大端模式\n");
}

网络字节序采用的是大端模式

网络接口 socket

网络通信接口 socket是一个简单易上手,功能强大的接口

有以下特点:

1.socket是一个编程接口(网络编程接口)

所有的网络程序,都需要基于socket

2.socket也是一个特殊的文件描述符

特殊:可以利用系统文件接口

比如 read write close

但是不能用lseek

它的内容不在文件系统中,也不在内核中,而是在"网络"中

3.socket 是TCP/IP协议的一种代码实现

但是它不仅限于TCP/IP协议,它还支持蓝牙协议,wifi协议,unix域协议

socket独立于具体协议的网络程序接口,位于应用层与传输层之间,负责衔接应用层与传输层

网络通信

网络通信的实现—》 API(应用程序编程接口)

1.socket 创建一个套接字

2.bind 不动,将一个地址(网络应用地址:IP+传输协议+端口)与套接字绑定

3.listen 监听,用于设定服务器监听套接字(监听后就可以获得客户端的请求)

4.accpet 等待连接请求的到来

5.connect 用于发起连接请求

6.通信 数据收发

​ read/write

​ recv/send

​ recefrom/send_to

7.关闭套接字

close 套接字也就是一个文件描述符罢了

思考 在网络通信在,服务器和客户端 双方的通信流程图

在这里插入图片描述

1 socket

NAMEsocket - create an endpoint for communicationSYNOPSIS#include <sys/types.h>          /* See NOTES */#include <sys/socket.h>socket用来创建一个通信接口int socket(int domain, int type, int protocol);@domain:指定域,协议族AF_UNIX, AF_LOCAL   Local communication              unix(7)unix域协议/本地协议栈AF_INET             IPv4 Internet protocols          ip(7)IPV4协议族AF_INET6            IPv6 Internet protocols          ipv6(7)IPV6协议族@type:指定套接字类型(选择传输层协议)SOCK_STREAM 流式套接字,面向TCP传输层协议SOCK_DGRAM  数据报套接字,面向UDP传输层协议SOCK_RAW	原始套接字@protocol:协议,指定具体那个协议一般为0,表示默认返回值:成功返回一个整数,是一个套接字文件描述符失败返回-1,并且errno被设置

2 bind

用于绑定服务器地址(IP+传输层协议+端口号)

NAMEbind - bind a name to a socketSYNOPSIS#include <sys/types.h>          /* See NOTES */#include <sys/socket.h>bind 绑定一个"名字”给socket(套接字描述符)int bind(int sockfd, const struct sockaddr *addr,socklen_t addrlen);@sockfd:指定套接字描述符,就是socket的返回值@addr:指向struct sockaddr 结构体指针,保存的是要绑定的地址@addrlen:地址长度,即参数addr的长度,sizeof (struct sockaddr)返回值:成功返回0,失败返回-1,并且errno被设置

关于网络应用的地址 =IP+传输层协议+端口号

在 头文件<sys/socket.h>中,定义了一个通用的网络应用地址结构体

struct sockaddr {sa_family_t sa_family;//指定协议栈,和socket函数的参数domain相同char        sa_data[14];//数组保存网络应用地址(IP+传输层协议+端口号)}

上面这个结构体,并不是很好赋值和使用,一般在网络编程中,网络应用地址赋值可以采用定义在

/usr/include/netinet/in.h中的结构体 struct sockaddr_in

Structure describing an Internet socket address

以太网地址结构体

struct sockaddr_in{__SOCKADDR_COMMON (sin_);//协议栈   sin_familyin_port_t sin_port;			/* 端口号,网络上一般是大端模式,计算机一般是小端模式  */struct in_addr sin_addr;		/* 指定ip地址. typedef uint32_t in_addr_t;struct in_addr{in_addr_t s_addr;};*//* Pad to size of `struct sockaddr'.  */unsigned char sin_zero[sizeof (struct sockaddr) -__SOCKADDR_COMMON_SIZE -sizeof (in_port_t) -sizeof (struct in_addr)];};

eg:某个网络应用

ip 172.2.1.11

端口 6666

struct sockaddr_in addr;//定义一个网络应用地址结构体addr
addr.sin_family=AF_INET;//协议族
addr.sin_port = htons(6666);//端口号是网络字节序,短整型
addr.sin_addr.s_addr = inet_addr(172.2.1.11);//点分式IP转为32bit整数
int ret = 0;//返回值
ret = bind(sockfd,(struct sockaddr)&addr,sizeof(addr));
if(ret == -1)
{perror("bind error");return -1;
}
//bind 之后,进程就有了一个网络应用地址,能够进行网络通信

端口本地字节序转网络字节序

h host 主机

to 转换成

n network 网络

s short 16bit

l long 32bit

NAMEhtonl, htons, ntohl, ntohs - convert values between host and network byte orderSYNOPSIS#include <arpa/inet.h>uint32_t htonl(uint32_t hostlong);将本地字节序转换成网络长整型uint16_t htons(uint16_t hostshort);将本地字节序转换成网络短整型uint32_t ntohl(uint32_t netlong);将网络字节序转换成本地长整型uint16_t ntohs(uint16_t netshort);将网络字节序转换成本地短整型参数就是需要转换的数据返回值就是转换之后的数据

点分式ip与32bit ip的转换

NAMEinet_aton, inet_addr, inet_network, inet_ntoa, inet_makeaddr, inet_lnaof, inet_netof - Internet address manipulation routinesSYNOPSIS#include <sys/socket.h>#include <netinet/in.h>#include <arpa/inet.h>inet_addr是用来将cp指定的点分式ip转换成32bit整数ip返回in_addr_t inet_addr(const char *cp);@cp 指针,指向要转换的点分式字符串ip成功返回转换后的32bit整数

网络通信

网络通信的实现—》 API(应用程序编程接口)

1.socket 创建一个套接字

2.bind 不动,将一个地址(网络应用地址:IP+传输协议+端口)与套接字绑定

3.listen 监听,用于设定服务器监听套接字(监听后就可以获得客户端的请求)

4.accpet 等待连接请求的到来

5.connect 用于发起连接请求

6.通信 数据收发

​ read/write

​ recv/send

​ recefrom/send_to

7.关闭套接字

close 套接字也就是一个文件描述符罢了

思考 在网络通信在,服务器和客户端 双方的通信流程图

在这里插入图片描述

1 socket

NAMEsocket - create an endpoint for communicationSYNOPSIS#include <sys/types.h>          /* See NOTES */#include <sys/socket.h>socket用来创建一个通信接口int socket(int domain, int type, int protocol);@domain:指定域,协议族AF_UNIX, AF_LOCAL   Local communication              unix(7)unix域协议/本地协议栈AF_INET             IPv4 Internet protocols          ip(7)IPV4协议族AF_INET6            IPv6 Internet protocols          ipv6(7)IPV6协议族@type:指定套接字类型(选择传输层协议)SOCK_STREAM 流式套接字,面向TCP传输层协议SOCK_DGRAM  数据报套接字,面向UDP传输层协议SOCK_RAW	原始套接字@protocol:协议,指定具体那个协议一般为0,表示默认返回值:成功返回一个整数,是一个套接字文件描述符失败返回-1,并且errno被设置

2 bind

用于绑定服务器地址(IP+传输层协议+端口号)

NAMEbind - bind a name to a socketSYNOPSIS#include <sys/types.h>          /* See NOTES */#include <sys/socket.h>bind 绑定一个"名字”给socket(套接字描述符)int bind(int sockfd, const struct sockaddr *addr,socklen_t addrlen);@sockfd:指定套接字描述符,就是socket的返回值@addr:指向struct sockaddr 结构体指针,保存的是要绑定的地址@addrlen:地址长度,即参数addr的长度,sizeof (struct sockaddr)返回值:成功返回0,失败返回-1,并且errno被设置

关于网络应用的地址 =IP+传输层协议+端口号

在 头文件<sys/socket.h>中,定义了一个通用的网络应用地址结构体

struct sockaddr {sa_family_t sa_family;//指定协议栈,和socket函数的参数domain相同char        sa_data[14];//数组保存网络应用地址(IP+传输层协议+端口号)}

上面这个结构体,并不是很好赋值和使用,一般在网络编程中,网络应用地址赋值可以采用定义在

/usr/include/netinet/in.h中的结构体 struct sockaddr_in

Structure describing an Internet socket address

以太网地址结构体

struct sockaddr_in{__SOCKADDR_COMMON (sin_);//协议栈   sin_familyin_port_t sin_port;			/* 端口号,网络上一般是大端模式,计算机一般是小端模式  */struct in_addr sin_addr;		/* 指定ip地址. typedef uint32_t in_addr_t;struct in_addr{in_addr_t s_addr;};*//* Pad to size of `struct sockaddr'.  */unsigned char sin_zero[sizeof (struct sockaddr) -__SOCKADDR_COMMON_SIZE -sizeof (in_port_t) -sizeof (struct in_addr)];};

eg:某个网络应用

ip 172.2.1.11

端口 6666

struct sockaddr_in addr;//定义一个网络应用地址结构体addr
addr.sin_family=AF_INET;//协议族
addr.sin_port = htons(6666);//端口号是网络字节序,短整型
addr.sin_addr.s_addr = inet_addr(172.2.1.11);//点分式IP转为32bit整数
int ret = 0;//返回值
ret = bind(sockfd,(struct sockaddr)&addr,sizeof(addr));
if(ret == -1)
{perror("bind error");return -1;
}
//bind 之后,进程就有了一个网络应用地址,能够进行网络通信

端口本地字节序转网络字节序

h host 主机

to 转换成

n network 网络

s short 16bit

l long 32bit

NAMEhtonl, htons, ntohl, ntohs - convert values between host and network byte orderSYNOPSIS#include <arpa/inet.h>uint32_t htonl(uint32_t hostlong);将本地字节序转换成网络长整型uint16_t htons(uint16_t hostshort);将本地字节序转换成网络短整型uint32_t ntohl(uint32_t netlong);将网络字节序转换成本地长整型uint16_t ntohs(uint16_t netshort);将网络字节序转换成本地短整型参数就是需要转换的数据返回值就是转换之后的数据

点分式ip与32bit ip的转换

NAMEinet_aton, inet_addr, inet_network, inet_ntoa, inet_makeaddr, inet_lnaof, inet_netof - Internet address manipulation routinesSYNOPSIS#include <sys/socket.h>#include <netinet/in.h>#include <arpa/inet.h>inet_addr是用来将cp指定的点分式ip转换成32bit整数ip返回in_addr_t inet_addr(const char *cp);@cp 指针,指向要转换的点分式字符串ip成功返回转换后的32bit整数

3 listen

设置监听,用于监听网络上是否有客户端向“我”(服务器)发起链接请求

NAMElisten - listen for connections on a socketSYNOPSIS#include <sys/types.h>          /* See NOTES */#include <sys/socket.h>int listen(int sockfd, int backlog);@sockfd:指定要监听的套接字描述符@backlog:监听数量,大于0就行了返回值:成功返回0  失败返回-1,并且errno被设置

listen设置去监听套接字描述符,以便知道是否有人(客户端)向我(服务器)发起链接请求

但是listen只监听,不处理链接

Eg:

int ret = 0;
ret = listen(sockfd,10);
if (ret == -1)
{perror("listen error");
}

4 accept

用于等待链接请求,并且处理链接请求

accpet会阻塞进程的运行,直到客户端向服务器发起了链接请求(客户端调用了connect)

NAMEaccept, accept4 - accept a connection on a socketSYNOPSIS#include <sys/types.h>          /* See NOTES */#include <sys/socket.h>int accept(int sockfd, struct sockaddr *addr, socklen_t *addrlen);@sockfd:指定套接字描述符@addr:指向struct sockaddr 结构体空间地址用于存储客户端的地址@addrlen:socklen_t空间地址addrlen参数在使用前,需要先赋值 参数addr的长度因为在函数内部,会先利用addrlen的值来确保捕获导致内存溢出返回值:成功返回一个非负数,该值是一个文件描述符===》链接套接字描述符用于 服务器与链接的客户端的通信接口也就是说服务器是提供accept的返回值 来收发客户端的消息失败 返回-1,并且errno被设置

eg:

struct sockaddr_in caddr;//用于保存客户端的地址
socklen_t caddr_len = sizeof(caddr);//保存客户端地址长度,使用前保存该地址空间的长度
int connfd = 0;//用于保存 链接套接字描述符
connfd = accept(sockfd,(struct sockaddr*)&caddr,$caddr_len);
if(connfd == -1)
{perror("accept error");return -1;
}

如果accept指向成功,则connfd就是服务器与客户端之间的通信接口

如果我们是多次调用accept,那么九年允许多个客户端连接,并且每个客户端连接上来后

服务器上都有一一对应的connfd

5 connect

用于客户端向服务器发起链接请求

NAMEconnect - initiate a connection on a socketSYNOPSIS#include <sys/types.h>          /* See NOTES */#include <sys/socket.h>int connect(int sockfd, const struct sockaddr *addr,socklen_t addrlen);@sockfd:指定套接字描述符@addr:指定要连接的服务器的地址@addrlen:addr的长度返回值:成功返回0失败返回-1,并且errno被设置

客户端调用 connect发起连接请求后,服务器的acceot接收到连接请求,并返回一个connfd用于服务器与客户端的通信接口

此时,客户端写入/发送数据给sockfd的数据就会通过网络传递给服务器的connfd

服务器就可以从connfd中读取/接收 这些数据

eg:

int ret = 0;
struct sockaddr_in saddr;
saddr.sin_family=AF_INET;//IPV4协议族
saddr.sin_port = htons(6666);//端口号是网络字节序,短整型
saddr.sin_addr.s_addr = inet_addr(172.2.1.110);//客户端的ip
ret = connect(sockfd,(struct sockaddr*)&saddr,sizeof(saddr));
if (ret == -1)
{perror("connect error");return -1;
}

6 数据收发

1 read/write

socket的网络通信,其利用的是文件描述符(符合Linux的设计哲学)

2 recv/send 接收/发送

recv 结束

NAMErecv, recvfrom, recvmsg - receive a message from a socketSYNOPSIS#include <sys/types.h>#include <sys/socket.h>recv用于从指定的套接字描述符中接收数据(同read)ssize_t recv(int sockfd, void *buf, size_t len, int flags);@sockfd:指定套接字描述符,即从那个接收输入@buf:指向一块缓存区,用于存储接收到的数据@len:指定要接收的字节数@flags:接收标志位0 默认接收,带阻塞接收如果能接收到数据就接收数据如果不能接收到数据,就一直等待,直到接收到数据MSG_DONTWAIT  不阻塞接收如果能够接收到数据,则接收数据如果不能接收到数据,则直接返回返回值:>0 成功返回实际接收到的字节数0 什么都没有接收到-1 接收失败,并且errno被设置

send 发送

NAMEsend, sendto, sendmsg - send a message on a socketSYNOPSIS#include <sys/types.h>#include <sys/socket.h>send 用于向套接字描述符中发送数据ssize_t send(int sockfd, const void *buf, size_t len, int flags);@sockfd:指定套接字描述符,即发送到那里去@buf:指向要发送的数据@len:要发送的数据大小,单位字节@flags:发送标志位0 阻塞发送MSG_DONTWAIT 非阻塞发送返回值 成功返回实际发送的字节数(>=0)失败返回-1 并且errno被设置

3 recvfrom/sendto

从哪里接收/发送给谁

特点

recvfrom 可以保存是谁发送过来的数据(保存发送者的地址)

sendto 可以指定发送的对象(地址),定向发送

一般用于UDP通信,很少使用在TCP通信中?WHY?

因为TCP面向连接的通信,在通信前就已经要求通信双方建立连接

UDP是非连接的通信,所以他需要指定发送给谁,要保留发送者的地址

recvfrom

NAMErecv, recvfrom, recvmsg - receive a message from a socketSYNOPSIS#include <sys/types.h>#include <sys/socket.h>ssize_t recvfrom(int sockfd, void *buf, size_t len, int flags,struct sockaddr *src_addr, socklen_t *addrlen);@前面四个参数 同recv@src_addr:指向一个 struct sockaddr缓存区(地址),用于存储对方的地址@addrlen:指向一个 socklen_t缓存区(地址)用于存储对方地址的长度src_addr和addrlen的使用,参考accept函数

sendto

NAMEsend, sendto, sendmsg - send a message on a socketSYNOPSIS#include <sys/types.h>#include <sys/socket.h>ssize_t sendto(int sockfd, const void *buf, size_t len, int flags,const struct sockaddr *dest_addr, socklen_t addrlen);@前四个参数 同send@dest_addr:指向一个 struct sockaddr缓存区(地址),表示发送给谁@addrlen:即dest_addr的长度

4 recvmsg/sendmsg

以结构体的形式 发送数据/接收数据

7 关闭套接字

套接字: socket 套接字描述符

服务器:用于监听,看是否有客户端发起连接请求

客户端:用于客户端与服务器的通信接口

close 关闭套接字

shutdown

NAMEshutdown - shut down part of a full-duplex connectionSYNOPSIS#include <sys/socket.h>shutdown用于关闭一个链接通道int shutdown(int sockfd, int how);@sockfd:指定套关闭那个链接通道@how:怎样关闭SHUT_RD 关闭读SHUT_WR 关闭写SHUT_RDWR 关闭读写返回值:成功返回0失败返回-1,并且errno被设置

eg:我们搭建的服务器,只获取客户端的信息,而不用给客户端发送信息

则可以关闭链接套接字的写功能

shutdown(connfd,SHUT_WR); //connfd 就变成了只读

结合已有函数和示例代码,查看流程图

尝试搭建一个TCP服务器

create_tcpserver 创建TCP服务器

1 创建socket套接字 网络通信接口

2 bind 绑定网络应用地址(便于其他应用找到本程序的通信接口)

3 listen 设置监听(内核监听是否有客户端向服务器发起连接请求)

mian

1 创建服务器 create_tcpserver

2 等待客户端的连接请求,并于客户端建立连接 accept的返回值connfd就是一个用来与客户端通信的描述符

(链接套接字描述符)

3 根据需求,编写与客户端的通信

案例:实现Ubuntu与开发板互相通信

点此跳转查看案例源码

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.xdnf.cn/news/139105.html

如若内容造成侵权/违法违规/事实不符,请联系一条长河网进行投诉反馈,一经查实,立即删除!

相关文章

【C++】模板初阶

今天开始将图片的水印全部去掉&#xff0c;以方便大家的观看和知识截屏分享&#xff0c;希望对大家都有所帮助 模板初阶目录&#xff1a; 一、什么是泛型编程&#xff08;编写与类型无关的代码&#xff09; 二、函数模板 2.1概念与格式 2.2底层原理 2.3实例化&#xff08;…

基于Spring Boot的网上购物商城系统

目录 前言 一、技术栈 二、系统功能介绍 用户功能模块的实现 管理员功能模块的实现 商家功能模块的实现 三、核心代码 1、登录模块 2、文件上传模块 3、代码封装 前言 本课题是根据用户的需要以及网络的优势建立的一个基于Spring Boot的网上购物商城系统&#xff0c;…

记录一次错误---想让U-net网络输入大小不一致的图片

最近在看Deeplab系列的论文&#xff0c;文中提到了语义分割领域的一个难题是&#xff1a;将图片输入网络之前需要resize成统一大小&#xff0c;但是resize的话会造成细节信息的损失&#xff0c;所以想要网络处理任意大小的图片输入。我之前训练的U-net网络都是resize成224*224大…

极简解析!IP计费的s5爬虫IP

大家好&#xff01;今天我将为大家分享关于s5爬虫IP服务的知识。对于经常做爬虫的小伙伴来说&#xff0c;需要大量的爬虫IP支持爬虫业务&#xff0c;那么对于选择什么样的爬虫IP&#xff0c;我想我有很多发言权。 下面我们一起了解下IP计费的s5爬虫IP的知识&#xff0c;废话不…

uniapp 内容展开组件

uni-collapse折叠面板并不符合需求&#xff0c;需要自己写一个。 效果展示&#xff1a; 代码&#xff1a; &#xff08;vue3版本&#xff09; <template><view class"collapse-view"><view class"collapse-content"><swiper:autopl…

AIMS医院手术麻醉信息系统全套源码,自主版权,开箱即用

手术麻醉临床信息系统有着完善的临床业务功能&#xff0c;能够涵盖整个围术期的工作&#xff0c;能够采集、汇总、存储、处理、展现所有的临床诊疗资料。通过该系统的实施&#xff0c;能够规范麻醉科的工作流程&#xff0c;实现麻醉手术过程的信息数字化&#xff0c;自动生成麻…

Dubbo3应用开发—Dubbo序列化方案(Kryo、FST、FASTJSON2、ProtoBuf序列化方案的介绍和使用)

Dubbo序列化方案&#xff08;Kryo、FST、FASTJSON2、ProtoBuf序列化方案的介绍和使用&#xff09; 序列化简介 序列化是Dubbo在RPC中非常重要的一个组成部分&#xff0c;其核心作用就是把网络传输中的数据&#xff0c;按照特定的格式进行传输。减小数据的体积&#xff0c;从而…

数据中心液冷服务器详情说明

目录 前言 何为液冷服务器&#xff1f; 为什么需要液冷&#xff1f; 1.数据中心降低PUE的需求 2.政策导向 3.芯片热功率已经达到风冷散热极限 4.液冷比热远大于空气 液冷VS风冷&#xff0c;区别在哪&#xff1f; 1.液冷服务器跟风冷服务器的区别 2.液冷数据中心跟风冷…

前端技术社区总目录

前端技术社区欢迎您的订阅。订阅后&#xff0c;您将可以查看以下所有博客内容。 注&#xff1a;专栏内容主要面向新手 注&#xff1a;每个示例都有相对应的完整代码 注&#xff1a;该专栏博客内容将会逐步迁移至https://blog.csdn.net/m0_60387551/article/details/128017725 …

Ubuntu修改静态IP、网关和DNS的方法总结

Ubuntu修改静态IP、网关和DNS的方法总结 ubuntu系统&#xff08;其他debian的衍生版本好像也可以&#xff09;修改静态IP有以下几种方法。&#xff08;搜索总结&#xff0c;可能也不太对&#xff09; /etc/netplan (use) Ubuntu 18.04开始可以使用netplan配置网络&#xff0…

数学建模——统计回归模型

一、基本知识 1、基本统计量 总体&#xff1a;研究对象的某个感兴趣的指标。样本&#xff1a;从总体中随机抽取的独立个体X1,X2,…,Xn&#xff0c;一般称(X1,…,Xn)为一个样本&#xff0c;可以看成一个n维随机向量&#xff0c;它的每一取组值(x1,…,xn)称为样本的观测值。统计…

哈希 -- 开散列

unordered_map和unordered_set 哈希/散列 -- 值跟存储位置建立映射关系 当不同的值映射到了相同的位置 -- 哈希冲突 / 哈希碰撞 开放定址法&#xff1a; a.线性探测 b.二次探测 负载因子&#xff1a; 越大冲突概率越大 越小冲突的概率越小 但是当负载因子到一个基准值…

yolov5的改进思想

Yolo v5一共有四个模型,分别为Yolov5s、Yolov5m、Yolov5l、Yolov5x。 Yolov5s网络最小,速度最少,AP精度也最低,如果检测的以大目标为主,追求速度,倒也是个不错的选择。 其他的三种网络,在此基础上,不断加深加宽网络,AP精度也不断提升,但速度的消耗也在不断增加。 …

黄金代理如何选择平台?窍门在这儿

作为一个黄金代理平台&#xff0c;什么才是最重要的呢&#xff1f;笔者认为以下三个方面是最重要的&#xff0c;一个是资质&#xff0c;第二个是口碑&#xff0c;第三个是平台的软件。这三者是成为黄金代理要考虑的最重要的三个因素&#xff0c;也直接关系大黄金代理的职业生涯…

ESP32低功耗蓝牙BLE通信

ESP32低功耗蓝牙BLE通信 蓝牙分类GATT协议GATT角色ESP32蓝牙简介ESP32开发板作为BLE服务设备或扫描设备手机APP连接作为BLE Server的ESP32总结 蓝牙分类 经典蓝牙Classic Bluetooth&#xff09;&#xff1a;用于数据量比较大的传输&#xff0c;如&#xff1a;图像、视频、音乐…

GaussDB技术解读系列:性能调优

近日&#xff0c;在第14届中国数据库技术大会&#xff08;DTCC2023&#xff09;的GaussDB“五高两易”核心技术&#xff0c;给世界一个更优选择专场&#xff0c;华为数据库技术专家李士福详细解读了GaussDB性能调优的相关技术和应用实践。 本篇为大家分享GaussDB性能调优的实践…

网络爬虫——HTTP和HTTPS的请求与响应原理

目录 一、HTTP的请求与响应 二、浏览器发送HTTP请求的过程 三、HTTP请求方法 四、查看网页请求 五、常用的请求报头 六、服务端HTTP响应 七、常用的响应报头 八、Cookie 和 Session 九、响应状态码 十、网页的两种加载方法 十一、认识网页源码的构成 十二、爬虫协议…

【大数据开发技术】实验04-HDFS文件创建与写入

文章目录 一、实验目标二、实验要求三、实验内容四、实验步骤 一、实验目标 熟练掌握hadoop操作指令及HDFS命令行接口掌握HDFS原理熟练掌握HDFS的API使用方法掌握单个本地文件写入到HDFS文件的方法掌握多个本地文件批量写入到HDFS文件的方法 二、实验要求 给出主要实验步骤成…

uniapp——ios证书申请——详细步骤+遇到的坑——技能提升

三年前&#xff0c;我曾经写过uniapp的程序&#xff0c;时隔三年&#xff0c;又遇到了uniapp的需求&#xff0c;之前没有自行申请ios证书&#xff0c;现在终于要自己生成证书了。。。 是福不是祸&#xff0c;是祸躲不过。 uniapp生成ios证书的详细步骤 uniapp对接unipush的操作…

buuctf web [ACTF2020 新生赛]Upload

明了但不明显的文件上传 传个试试 行&#xff0c;抓包吧&#xff0c;php格式不行&#xff0c;就先上传要求的格式&#xff1a;jpg、png、gif 抓到上传的包之后&#xff0c;再修改成我们想要的 常见的php格式绕过有&#xff1a;php,php3,php4,php5,phtml,pht 挨个试试 这是上个…