由浅到深认识C语言(11):结构体

该文章Github地址:https://github.com/AntonyCheng/c-notes

在此介绍一下作者开源的SpringBoot项目初始化模板(Github仓库地址:https://github.com/AntonyCheng/spring-boot-init-template & CSDN文章地址:https://blog.csdn.net/AntonyCheng/article/details/136555245),该模板集成了最常见的开发组件,同时基于修改配置文件实现组件的装载,除了这些,模板中还有非常丰富的整合示例,同时单体架构也非常适合SpringBoot框架入门,如果觉得有意义或者有帮助,欢迎Star & Issues & PR!

上一章:由浅到深认识C语言(10):字符串处理函数

11.结构体

概念以及定义:

C 语言允许用户自己指定这样一种数据结构,它由不同类型的数据组合成一个整体,以便引用,这些组合在一个整体中的数据是互相联系的,这样的数据结构称为结构体,它相当于其它高级语言中记录;

11.1.结构体定义形式

**形式一:**先定义结构体类型,再定义变量(推荐);

//定义结构体类型
struct 结构体类型{成员一;成员二;……
};
//定义变量
struct 结构体类型 变量名;

示例如下:

struct stu{int id;char name[5];int age;
};
struct stu s1;

此时结构体的数据类型就是定义时中括号前的内容,即 struct stu

**形式二:**定义类型的同时定义变量;

//定义类型,同时定义变量
struct 结构体类型{成员一;成员二;……
}变量名;

示例如下:

struct stu{int id;char name[5];int age;
}s1;

**形式三:**定义一次性结构体;

//定义类型,但不带结构体类型,同时定义变量
struct {成员一;成员二;……
}变量名;

示例如下:

struct{int id;char name[5];int age;
}s1;

不能用一次性结构体定义其他变量,例如 s2 、s3 ……

注意事项

  • 定义结构体类型的时候,不要给成员变量赋值,因为定义结构体类型的时候并没有分配空间,所以结构体类型不占空间,结构体变量才占空间
  • 结构体内的成员拥有独立的空间;
  • 定义结构体类型是一条语句,所以要记住结构体后的那一个 ;

实例展示

#include<stdio.h>struct stu
{int id;char name[32];int age;
};void test() {printf("sizeof(struct stu) = %d\n", sizeof(struct stu));return;
}int main(int argc, char* argv[]) {test();return 0;
}

打印效果如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

11.2.结构体使用法则

格式:类似于Java中类的思想;

结构体变量.结构体成员

访问结构体成员时是通过结构体变量来访问的,而且一定要遵循成员自身的类型;

重点又是字符串在结构体中的操作,字符串除了初始化能够直接赋值之外,其他情况的赋值必须想其他方法,而在结构体中是不能在结构体中成员进行初始化的,所以我们就要将字符串拷贝进去;

示例如下:

#include<stdio.h>
#include<string.h>struct stu
{int id;char name[32];int age;
};void test() {struct stu xiaochen;xiaochen.id = 9;strcpy_s(xiaochen.name, 32, "晓晨");xiaochen.age = 21;printf("xiaochen.id = %d\n", xiaochen.id);printf("xiaochen.name = %s\n", xiaochen.name);printf("xiaochen,age = %d\n", xiaochen.age);return;
}int main(int argc, char* argv[]) {test();return 0;
}

打印效果如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

11.3.结构体的操作

初始化结构体

定义结构体类型的时候我们是不能将其初始化的,但是在定义变量时可以对其进行初始化;

初始化示例如下:

struct stu{int id;char name[32];char sex;
};
struct stu s = {2020510,"xiaochen",'男'};

清空结构体

格式如下:

struct stu{int id;char name[32];char sex;
};
struct stu s = {2020510,"xiaochen",'男'};
memset(&s, 0, sizeof(s));

11.4.结构体变量操作

获取键盘输入

示例如下:

#include<stdio.h>
#include<string.h>struct stu
{int id;char name[32];int age;
};void test() {struct stu xiaochen;memset(&xiaochen, 0, sizeof(xiaochen));printf("从键盘输入xiaochen的基本情况:");scanf_s("%d %s %d", &xiaochen.id, xiaochen.name, 32, &xiaochen.age);printf("xiaochen.id = %d\n", xiaochen.id);printf("xiaochen.name = %s\n", xiaochen.name);printf("xiaochen.age = %d\n", xiaochen.age);
}int main(int argc, char* argv[]) {test();return 0;
}

打印效果如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

变量之间的赋值

例如此时有两个结构体变量,我们想将其中一个的值复制给另外一个,此时就要使用到变量之间的赋值运算;

**方式一:**逐个成员更换;

#include<stdio.h>
#include<string.h>struct stu
{int id;char name[32];int age;
};void test() {struct stu s1 = { 2022,"小红",21 };struct stu s2;s2.age = s1.age;s2.id = s1.id;strcpy_s(s2.name, 32, s1.name);printf("s2.age = %d , s2.id = %d , s2.name = %s\n", s2.age, s2.id, s2.name);
}int main(int argc, char* argv[]) {test();return 0;
}

打印效果如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

**方式二:**相同类型的结构体变量可以整体赋值;(推荐)

#include<stdio.h>
#include<string.h>struct stu
{int id;char name[32];int age;
};void test() {struct stu s1 = { 2022,"小红",21 };struct stu s2;s2 = s1;printf("s2.age = %d , s2.id = %d , s2.name = %s\n", s2.age, s2.id, s2.name);
}int main(int argc, char* argv[]) {test();return 0;
}

打印效果如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

**方式三:**使用内存拷贝函数 memcpy() 从原理出发实现赋值;

#include<stdio.h>
#include<string.h>struct stu
{int id;char name[32];int age;
};void test() {struct stu s1 = { 2022,"小红",21 };struct stu s2;memcpy(&s2, &s1, sizeof(s1));printf("s2.age = %d , s2.id = %d , s2.name = %s\n", s2.age, s2.id, s2.name);
}int main(int argc, char* argv[]) {test();return 0;
}

打印效果如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

11.5.结构体数组操作

结构体数组本质就是装有结构体的数组容器;

图解:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

当我们要去提取 arr[2] 中的 name ,即用 arr[2].name

示例如下:

#include<stdio.h>
#include<string.h>struct stu
{int id;char name[32];int age;
};void test() {struct stu arr[5] = {{100,"xiaofa",18},{101,"xiaohong",19},{102,"xiaowang",18},{103,"xiaochen",19},{104,"xiaowu",20}};for (int i = 0; i < 5; i++) {printf("arr[%d].id = %d , arr[%d].name = %s , arr[%d].age = %d\n",i,arr[i].id,i,arr[i].name,i,arr[i].age);}
}int main(int argc, char* argv[]) {test();return 0;
}

打印效果如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

结构体数组从键盘输入:

#include<stdio.h>
#include<string.h>struct stu
{int id;char name[32];int age;
};void test() {struct stu arr[5];int n = sizeof(arr) / sizeof(arr[0]);memset(arr, 0, sizeof(arr));printf("请一次输入%d个学生的学号,名字以及年龄:\n", n);for (int i = 0; i < n; i++) {printf("请输入第%d个学生的信息:\n",i+1);scanf_s("%d %s %d", &arr[i].id, arr[i].name, 32, &arr[i].age);}for (int i = 0; i < n; i++) {printf("arr[%d].id = %d , arr[%d].name = %s , arr[%d].age = %d\n",i,arr[i].id,i,arr[i].name,i,arr[i].age);}
}int main(int argc, char* argv[]) {test();return 0;
}

打印效果如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

11.6.结构体指针操作

顾名思义,结构体指针本质是指针,该指针指向结构体的地址,即数据类型是一个 结构体*

写法类比:

//定义结构体:
struct struct_name{int id;};
//定义结构体变量:
struct struct_name a;
//定义结构体指针变量:
struct struct_name* p;
//结构体变量调用结构体元素:
a.id;
//结构体指针变量调用结构体元素:
a->id;  //也可以写作(*a).id;

图解如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

示例一:结构体指针;

#include<stdio.h>
#include<string.h>struct stu
{int id;char name[32];int age;
}; void test() {struct stu xiaochen = { 100,"晓晨",18 };printf("id = %d,name = %s,age = %d\n", xiaochen.id, xiaochen.name, xiaochen.age);struct stu* p = &xiaochen;p->age = 20;p->id = 101;strcpy_s(p->name, 32, "安东尼");printf("id = %d,name = %s,age = %d\n", xiaochen.id, xiaochen.name, xiaochen.age);
}int main(int argc, char* argv[]) {test();return 0;
}

打印效果如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

案例二:从堆区为结构体申请一个空间;

#include<stdio.h>
#include<stdlib.h>
#include<string.h>struct stu
{int id;char name[32];int age;
}; void test() {struct stu* p = NULL;int n = 0;printf("请输入人数个数:");scanf_s("%d", &n);//从堆区申请结构体空间p = (struct stu*)calloc(n, sizeof(struct stu));if (p == NULL) {perror("err");return;}//获取键盘输入for (int i = 0; i < n; i++) {printf("请输入第%d个学生信息:", i + 1);scanf_s("%d %s %d", &(p+i)->id, (p+i)->name,32, &(p+i)->age);}//遍历键盘输入for (int i = 0; i < n; i++) {printf("p.id = %d  p.name = %s  p.age = %d\n", (p+i)->id, (p+i)->name, (p+i)->age);}//释放空间if (p != NULL) {free(p);p = NULL;}
}int main(int argc, char* argv[]) {test();return 0;
}

打印效果如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

示例三:从堆区为结构体数组申请一个空间,并且分函数实现(空间复杂度尽可能地小);

#include<stdio.h>
#include<stdlib.h>
#include<string.h>struct stu
{int id;char name[32];int age;
};struct stu* get_mem(int n) {return (struct stu*)calloc(n, sizeof(struct stu));
}struct stu* set_data(struct stu* p, int* n) {for (int i = 0; i < *n; i++) {printf("请输入第%d个同学信息:", i + 1);scanf_s("%d %s %d", &(p + i)->id, (p + i)->name, 32, &(p + i)->age);}return p;
}void print_data(const struct stu* p, int* n) {//constfor (int i = 0; i < *n; i++) {printf("student%d.id = %d  student%d.name = %s student%d.age = %d\n", i + 1, (p + i)->id, i + 1, (p + i)->name, i + 1, (p + i)->age);}return;
}void test() {printf("请输入学生的个数:\n");int n;scanf_s("%d", &n);struct stu* arr = NULL;//根据学生个数申请空间arr = get_mem(n);if (arr == NULL) {perror("err");return;}//为申请的空间赋值arr = set_data(arr, &n);//输出空间内容print_data(arr, &n);//释放空间if (arr != NULL) {free(arr);arr = NULL;}
}int main(int argc, char* argv[]) {test();return 0;
}

打印效果如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

结构体指针作为函数的参数

**示例一:**定义一个函数,给结构体成员获取键盘输入;

#include<stdio.h>
#include<stdlib.h>
#include<string.h>struct stu
{int id;char name[32];int age;
}; void method(struct stu* student) {printf("请输入学生的信息(学号 名字 年龄):");scanf_s("%d %s %d", &student->id, student->name, 32, &student->age);printf("xiaochen.id = %d  xiaochen.name = %s  xiaochen.age = %d\n", student->id, student->name, student->age);
}void test() {struct stu xiaochen;method(&xiaochen);
}int main(int argc, char* argv[]) {test();return 0;
}

打印效果如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

11.7.typedef取别名

使用步骤:

  • 先用已有的类型定义一个相对应的变量
  • 用别名替换变量名
  • 在整个表达式前添加 typedef

注意:typedef 不能创造新的类型,只是给现有类型取别名;

给 int 类型取别名:

#include<stdio.h>typedef int INT;void test() {INT num = 10;printf("INT num = %d\n", num);
}int main(int argc, char* argv[]) {test();return 0;
}

打印效果如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

给数组取别名:

#include<stdio.h>typedef int INT[5];void test() {INT num = {1,2,3,4,5};  //此时 arr 就是一个拥有5个元素,每个元素为 int 型的数组,arr 是数组首地址for (int i = 0; i < 5; i++) {printf("%d ", *(num + i));}printf("\n");
}int main(int argc, char* argv[]) {test();return 0;
}

打印效果如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

给指针取别名:

#include<stdio.h>typedef int* INT;void test() {INT num = NULL;int a = 10;num = &a;printf("*num = %d\n", *num);
}int main(int argc, char* argv[]) {test();return 0;
}

打印效果如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

给函数指针取别名:

#include<stdio.h>int sum(int a, int b) {return a + b;
}typedef int (*SUM)(int,int) ;
//SUM 是一个函数指针类型,该函数必须有两个 int 形参以及一个 int返回值void test() {SUM p = sum;printf("*num = %d\n", p(100,200));
}int main(int argc, char* argv[]) {test();return 0;
}

打印效果如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

给结构体类型取别名:

#include<stdio.h>
#include<string.h>typedef struct stu
{int id;char name[32];int age;
}STU; //此时的STU不是结构体变量,而是结构体类型void test() {STU xiaochen = { 0 };xiaochen.age = 19;xiaochen.id = 101;strcpy_s(xiaochen.name, 32, "晓晨");printf("%s %d %d\n", xiaochen.name, xiaochen.id, xiaochen.age);
}int main(int argc, char* argv[]) {test();return 0;
}

打印效果如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

11.8.结构体内存对齐

引入实例:

#include<stdio.h>
struct data1
{char ch1;  //1Bchar ch2;  //1Bchar ch3;  //1Bshort num; //2B
};
struct data2
{char ch1;  //1Bchar ch2;  //1Bchar ch3;  //1Bint num;   //4B
};
struct data3
{char ch1;  //1Bchar ch2;  //1Bchar ch3;  //1Bdouble num;  //8B
};void test() {struct data1 d1;printf("sizeof(d1) = %d\n", sizeof(d1));struct data2 d2;printf("sizeof(d2) = %d\n", sizeof(d2));struct data3 d3;printf("sizeof(d3) = %d\n", sizeof(d3));
}int main(int argc, char* argv[]) {test();return;
}

打印效果如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

从上面例子所打印结果我们可以得到一个观察结论:

结构体的大小由占内存最大的那个基本数据类型所决定,即结构体的单位内存大小就是内存最大的基本数据类型的内存大小,这就是结构体的内存向大对齐;

结构体内存分布

示例如下:

struct data{char c;  //1Bint i;  //4B
};

方法如下:

  1. 确定分配单位:每一行应该分配的字节数;

    由结构体中最大的基本类型长度决定;

  2. 确定成员的起始位置的偏移量 == 成员的基本类型含零整数倍

  3. 收尾工作:结构体总大小 == 分配单位的整数倍;

案例一:

typedef struct {int a;char b;short c;char d;
}DATA;

画图如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

证实如下:

#include<stdio.h>typedef struct {int a;char b;short c;char d;
}DATA;void test() {DATA data = { 0,0,0,0 };printf("%u\n", &data.a);printf("%u\n", &data.b);printf("%u\n", &data.c);printf("%u\n", &data.d);
}int main(int argc, char* argv[]) {test();return;
}

打印效果如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

案例二:

typedef struct {char a;short b;short c;int d;char e;
}DATA;

画图如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

案例三:

typedef struct {char a;short b;char c;short d;
}DATA;

画图如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

结构体内存分布的作用

便于指针作用于结构体中;

示例如下:

一个结构体中有如下成员:

typedef struct {char a;int b;short c;
}DATA;

我们要通过指针去取到 short c

#include<stdio.h>typedef struct {char a;int b;short c;
}DATA;void test() {DATA data = { 'a',10,20 };char* p = NULL;p = &data.a;p = p + 8;printf("data.c = %d\n", *(short*)p);
}int main(int argc, char* argv[]) {test();return;
}

打印效果如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

11.9.结构体嵌套结构体

图解如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

示例如下:

#include<stdio.h>typedef struct {int a;int b;
}DATA1;typedef struct {int c;int d;DATA1 e;  //结构体变量c作为DATA2的成员,这就是结构体嵌套结构体
}DATA2;void test() {DATA2 data = {0,0,{0,0}};printf("请输入四个数字:\n");scanf_s("%d %d %d %d", &data.e.a, &data.e.b, &data.c, &data.d);printf("你输入的四个数是:\n");printf("data.e.a = %d\ndata.e.b = %d\ndata.c = %d\ndata.d = %d\n", data.e.a, data.e.b, data.c, data.d);
}int main(int argc, char* argv[]) {test();return;
}

打印效果如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

嵌套结构内存分布

该内存分布与单层结构体的内存分布方式大同小异;

方法如下:

  1. 确定分配单位:每一行应该分配的字节数;

    由所有结构体中最大的基本类型长度决定的;

  2. 确定成员的偏移量 == 自身类型的含零整数倍;

    结构体成员偏移量 == 被嵌套的结构体中最大的基本类型含零整数倍;

    结构体成员中的成员偏移量是相对于被嵌套的结构体而言的;

  3. 收尾工作:结构体的总大小 == 分配单位的整数倍;

    结构体成员的总大小 == 被嵌套的结构体里面最大基本类型整数倍;

案例一:

typedef struct {short d;char e;
}DATA2;typedef struct {short a;int b;DATA2 c;short f;
}DATA1;

画图如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

证实如下:

#include<stdio.h>typedef struct {short d;char e;
}DATA2;typedef struct {short a;int b;DATA2 c;short f;
}DATA1;void test() {DATA1 data = { 0,0,{0,0},0 };printf("%u\n", &data.a);printf("%u\n", &data.b);printf("%u\n", &data.c.d);printf("%u\n", &data.c.e);printf("%u\n", &data.f);
}int main(int argc, char* argv[]) {test();return;
}

打印效果如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

案例二:

typedef struct {short d;char e;
}DATA2;typedef struct {int a;short b;DATA2 c;short f;
}DATA;

画图如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

11.10.强制类型对齐

为了控制C语言中数据类型对齐不统一的问题,C语言中自带了一条处理语言:

#pragma pack (value);
//value只能是2^n,常用的几个是1,2,4,8;

这样声明就能够将该文件中的数据类型强制对齐于某一个值,但是要注意以下事项

指定对齐方式(value)与数据类型对齐默认值相比取较小值;

**解释说明:**如果我们指定的是 4,但是系统默认对齐值是 2 ,那么我们所设置的对齐方式无效,系统会默认进行比较,并且选择较小的值,如果我们指定的是 2,但是系统默认对齐值是 4,那么我们所设置的对齐方式就会生效;

  • 例一:指定值是 1,则 short、int、float 等均为 1;
  • 例二:指定值是 2,则 char 仍然为 1,short 为 2,int 也为 2;

下面是具体步骤:

  1. 确定分配单位:每一行应该分配的字节数 ==> min(value,默认分配单位);
  2. 成员偏移量 == 成员自身类型的含零整数倍;
  3. 收尾工作:总大小就是分配单位的整数倍;

那么我们可以通过强制类型对齐来计算一个结构体的真实大小,即不含有空地值的大小:

#include<stdio.h>
#pragma pack (1)
typedef struct {char a;    //1Bint b;     //4Bshort c;   //2B
}DATA;void test() {DATA data = { 'a',10,20 };printf("the real size of data is %d Bite\n", sizeof(data));
}int main(int argc, char* argv[]) {test();return 0;
}

打印效果如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

无论是系统默认对齐,还是强制类型转换都有可能会改变一个结构体的内存大小,除此之外,调整结构体的成员顺序也有可能改变一个结构体的大小,但是这是一个时间复杂度与空间复杂度的相互牵制问题,如果想让空间复杂度小一点,那么就尽量把数据类型大小相同的或者相近的成员在编写代码阶段编在一起;

下一章:由浅到深认识C语言(12):位段/位域

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

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【全开源】JAVA情侣扭蛋机情侣游戏系统源码支持微信小程序+微信公众号+H5

一、功能介绍 会员功能、情侣扭蛋 收到的券、送出的券 合伙代理、意见反馈 我们技术使用JAVA后台服务 前后端分离 springbootmybatisplusmysql 用户端 uniapp&#xff08;vue语法&#xff09;管理后台 vueelementUi 适配小程序H5公众号&#xff0c;一套源码&#xff0c;无…

Jenkins 面试题及答案整理,最新面试题

Jenkins中如何实现持续集成与持续部署&#xff1f; Jenkins通过自动化构建、测试和部署应用程序来实现持续集成与持续部署&#xff08;CI/CD&#xff09;。这个过程包括以下步骤&#xff1a; 1、源代码管理&#xff1a; Jenkins支持与多种版本控制系统集成&#xff0c;如Git、…

设计模式在芯片验证中的应用——装饰器

一、装饰器模式 装饰器模式(Decorator)是一种结构化软件设计模式&#xff0c;它提供了一种通过向类对象添加行为来修改类对象的方法&#xff0c;而不会影响同一类的其它对象行为。该模式允许在不修改抽象类的情况下添加类功能。它从本质上允许基类代码对不可预见的修改具有前瞻…

SQLiteC/C++接口详细介绍之sqlite3类(十二)

返回目录&#xff1a;SQLite—免费开源数据库系列文章目录 上一篇&#xff1a;SQLiteC/C接口详细介绍之sqlite3类&#xff08;十一&#xff09; 下一篇&#xff1a;SQLiteC/C接口详细介绍之sqlite3类&#xff08;十三&#xff09; ​37.sqlite3_load_extension 用于在SQLit…

Iframe 嵌入: 页面嵌入并保持自适应页面的宽高并铺满整个屏幕

文章目录 问题分析1. 嵌入 Iframe2. 样式3. 源码 问题 当我们使用 Iframe 嵌入页面后&#xff0c;会看到它只在小小的一部分进行展示&#xff0c;如何让它铺满整个屏幕 分析 1. 嵌入 Iframe <template><div><iframe :src"embeddedPageUrl" width…

R语言中的常用基础绘图函数 直方图,箱线图,条形图,散点图

目录 R语言中的绘图参数 绘图函数 1.plot函数绘制散点图 2.hist函数绘制直方图 如何修饰直方图? 如何在直方图上标注各组频数&#xff1f; 使用text函数把某些信息标注在直方图上 如何在直方图上添加概率密度曲线&#xff1f; 3.boxplot函数绘制箱线图 4.barplot函数…

【强化学习笔记一】初识强化学习(定义、应用、分类、性能指标、小车上山案例及代码)

文章目录 第1章 初识强化学习1.1 强化学习及其关键元素1.2 强化学习的应用1.3 强化学习的分类1.3.1 按任务分类1.3.2 按算法分类 1.4 强化学习算法的性能指标1.5 案例&#xff1a;基于Gym库的智能体/环境接口1.5.1 安装Gym库1.5.2 使用Gym库1.5.3 小车上山1.5.3.1 有限动作空间…

灯塔:CSS笔记(4)

伪类选择器&#xff1a; 1.作用与优势&#xff1a; 1.作用&#xff1a;根据元素在HTML中的结构关系查找元素 2.优势&#xff1a;减少对于HTML中类的依赖&#xff0c;有利于保持代码的整洁 3.场景&#xff1a;常用于查找某父级选择器中的子元素 2.选择器 选择器说明E:first-c…

蓝桥杯2023年省A(一波三折的)【买瓜】折半搜索+剪枝+排序

题目&#xff1a;洛谷 P9234 [蓝桥杯 2023 省 A] 买瓜 折半搜索 一开始觉得像dp&#xff0c;试着写了&#xff0c;显然过不了&#xff0c;但我实在觉得搜索也过不了啊&#xff0c;去看题解&#xff0c;发现使用了折半搜索&#xff08;每天都觉得啥都不会捏 折半搜索就是先搜一…

wayland(xdg_wm_base) + egl + opengles 渲染使用纹理贴图的旋转 3D 立方体实例(十三)

文章目录 前言一、使用 stb_image 库加载纹理图片1. 获取 stb_image.h 头文件2. 使用 stb_image.h 中的相关接口加载纹理图片3. 纹理图片——cordeBouee4.jpg二、渲染使用纹理贴图的旋转 3D 立方体1. egl_wayland_texture_cube.c2. Matrix.h 和 Matrix.c3. xdg-shell-client-pr…

日期与时间(Java)

文章目录 日期与时间&#xff08;Java&#xff09;一、JDK8之前的1.1 Date1.2 SimpleDateFormat1.3 Calendar 二、 JDK8之后的2.1 LocalDate、LocalTime和LocalDateTime2.2 ZoneId和ZonedDateTime2.3 Instant2.4 DateTimeFormatter2.4 Period和 Duration &#x1f389;写在最后…

鸿蒙Harmony应用开发—ArkTS声明式开发(基础手势:Web)下篇

onRequestSelected onRequestSelected(callback: () > void) 当Web组件获得焦点时触发该回调。 示例&#xff1a; // xxx.ets import web_webview from ohos.web.webviewEntry Component struct WebComponent {controller: web_webview.WebviewController new web_webv…

Github Copilot 工具,无需账号,一键激活

① 无需账号&#xff0c;100%认证成功&#xff01;0风险&#xff0c;可联网可更新&#xff0c;&#xff0c;支持copilot版本升级&#xff0c;支持chat ② 支持windows、mac、linux系统等设备 ③一号通用&#xff0c;支持所有IDE(AppCode,CLion,DataGrip,GoLand,IntelliJ IDEA …

Linux 基础-查看和设置环境变量

一&#xff0c;查看环境变量 在 Linux中&#xff0c;环境变量是一个很重要的概念。环境变量可以由系统、用户、Shell 以及其他程序来设定&#xff0c;其是保存在变量 PATH 中。环境变量是一个可以被赋值的字符串&#xff0c;赋值范围包括数字、文本、文件名、设备以及其他类型…

前端跨平台开发框架:简化多端开发的利器

&#x1f90d; 前端开发工程师、技术日更博主、已过CET6 &#x1f368; 阿珊和她的猫_CSDN博客专家、23年度博客之星前端领域TOP1 &#x1f560; 牛客高级专题作者、打造专栏《前端面试必备》 、《2024面试高频手撕题》 &#x1f35a; 蓝桥云课签约作者、上架课程《Vue.js 和 E…

OpenCV系列文章目录(持续更新中......)

引言&#xff1a; OpenCV是一个开源的计算机视觉库&#xff0c;由英特尔公司开发并开源的一组跨平台的C函数和少量的C函数组成&#xff0c;用于实时图像处理、计算机视觉和机器学习等应用领域。OpenCV可以在包括Windows、Linux、macOS等各种操作系统平台上使用&#xff0c;具…

用Origin快速拟合荧光寿命、PL Decay (TRPL)数据分析处理

需要准备材料&#xff1a;Origin、PL Decay数据txt文件 首先打开Origin画图软件 导入数据&#xff0c;按照下图箭头操作直接导入 双击你要导入的PL Decay的txt数据文件&#xff0c;然后点OK 继续点OK 数据导入后首先删除最大光子数之前的无效数据&#xff0c;分析的时候用…

计算机设计大赛 题目:基于机器视觉opencv的手势检测 手势识别 算法 - 深度学习 卷积神经网络 opencv python

文章目录 1 简介2 传统机器视觉的手势检测2.1 轮廓检测法2.2 算法结果2.3 整体代码实现2.3.1 算法流程 3 深度学习方法做手势识别3.1 经典的卷积神经网络3.2 YOLO系列3.3 SSD3.4 实现步骤3.4.1 数据集3.4.2 图像预处理3.4.3 构建卷积神经网络结构3.4.4 实验训练过程及结果 3.5 …

特殊内齿轮加工的另一种选择

内齿轮加工普遍采用插齿或拉削&#xff0c;但对于一些特殊齿廓的内齿轮来说&#xff0c;插齿可能会有一定的困难&#xff0c;或者成本较高。在这种情况下&#xff0c;线切割加工不失为一种不错的选择。那么什么样的零件需要选择这种加工方式呢&#xff1f;一起来看看&#xff1…

Mr-Robot1靶场练习靶场推荐小白入门练习靶场渗透靶场bp爆破wordpress

下载链接&#xff1a; Mr-Robot: 1 ~ VulnHub 安装&#xff1a; 打开vxbox&#xff0c;菜单栏----管理----导入虚拟电脑 选择下载完的ova文件&#xff0c;并修改想要保存的位置&#xff08;也可以保持默认位置&#xff09; 导入完成后可以根据自己的情况去配置网络链接方式 完成…