当前位置: 首页 > news >正文

C语言:指针和数组(看完拿捏指针和数组)

目录

数组名的理解:

一维数组:

 解析:

 字符数组:

 解析: 

 解析:

字符串数组:

 解析: 

 解析: 

一级指针: 

 解析: 

 解析: 

二维数组:

 解析: 

指针笔试题:

题一:一维数组

题二: 结构体指针

题三: 一维数组

题四: 二维数组

题五: 二维数组

题六: 二维数组

题七:指针数组

题八: 指针数组(多级)

以上就是个人学习见解和学习的解析,欢迎各位大佬在评论区探讨!

感谢大佬们的一键三连! 感谢大佬们的一键三连! 感谢大佬们的一键三连!


数组名的理解:

数组名是数组首元素的地址;
但是有2个例外
1. sizeof(数组名),这里的数组名表示整个数组,计算的是整个数组的大小,单位是字节;
2. &数组名,这里的数组名表示整个数组,取出的是整个数组的地址。

代码中的4/8指的是在32位或者X86环境下位4个字节,在X64环境下是8个字节。 

一维数组:

#include <stdio.h>
int main()
{int a[] = { 1,2,3,4 };printf("%d\n", sizeof(a));//16printf("%d\n", sizeof(a + 0));//4/8printf("%d\n", sizeof(*a));//4printf("%d\n", sizeof(a + 1));//4/8printf("%d\n", sizeof(a[1]));//4printf("%d\n", sizeof(&a));//4/8printf("%d\n", sizeof(*&a));//16printf("%d\n", sizeof(&a + 1));//4/8printf("%d\n", sizeof(&a[0]));//4/8printf("%d\n", sizeof(&a[0] + 1));//4/8return 0;
}

 解析:

1、sizeof(数组名),数组名表示整个数组,计算的是整个数组的大小,单位是字节。

2、a不是单独放在sizeof()内部,也没有取地址,所以a就是首元素的地址,a+0还是首元素的地址,是地址大小就是4/8个字节。

3、*a中的a是数组首元素的地址,*a就是对首元素的地址解引用,找到的就是首元素,首元素的大小就是4个字节。

4、这里的a是数组首元素的地址,a+1是第二个元素的地址,sizeof(a+1)就是地址的大小

5、计算的是第二个元素的大小。

6、&a取出的数组的地址,数组的地址也就是个地址。

7、&a----> int( * )[ 4 ],   *&a----->int [ 4 ]。

8、&a取出的是数组的地址,&a--> int( * )[ 4 ],&a+1是从数组a的地址向后跳过一个(4个整型元素)数组的大小,&a+1还是地址,是地址就是4/8个字节。

9、&a[ 0 ]就是第一个元素的地址,计算的是地址的大小,是地址就是4/8个字节。

10、&a[ 0 ]+1就是第二个元素的地址,大小是4/8个字节,&a[ 0 ]+1---> &a[ 1 ] 。

 字符数组:

#include <stdio.h>int main()
{char arr[] = {'a','b','c','d','e','f'};printf("%d\n", sizeof(arr));//6printf("%d\n", sizeof(arr+0));//4/8printf("%d\n", sizeof(*arr));//1printf("%d\n", sizeof(arr[1]));//1printf("%d\n", sizeof(&arr));//4/8printf("%d\n", sizeof(&arr+1));//4/8printf("%d\n", sizeof(&arr[0]+1));//4/8return 0;
}

 解析: 

1、//数组名单独放在sizeof内部,这里的arr表示整个数组,计算的是整个数组的大小,单位是字节,总共6个字节类型是char [6]。

2、//arr表示数组首元素的地址,arr+0还是数组首元素的地址,是地址就是4/8个字节,类型是char*。

3、//arr表示数组首元素的地址,*arr就是首元素,大小1个字节,类型是char。

4、//arr[1]就是第二个元素,大小是1个字节。

5、//&arr是数组的地址,但是数组的地址也是地址,是地址就是4/8。

6、//&arr + 1是跳过整个数组后的地址,是地址就是4/8个字节。

7、//第二个元素的地址,是4/8个字节。

#include <stdio.h>int main()
{char arr[] = {'a','b','c','d','e','f'};printf("%d\n", strlen(arr));//随机值printf("%d\n", strlen(arr+0));//随机值printf("%d\n", strlen(*arr));//错误printf("%d\n", strlen(arr[1]));//错误printf("%d\n", strlen(&arr));//随机值printf("%d\n", strlen(&arr+1));//随机值printf("%d\n", strlen(&arr[0]+1));//随机值return 0;
}

 解析:

1、因为字符数组arr中没有‘ \0 ’,所以在求字符串长度的时候,会一直往后找,产生的结构就是随机值。

2、arr + 0是首元素的地址,和第一个一样,也是随机值。

3、//错误, arr是数组首元素的地址,*arr就是数组首元素,就是'a'-97;
//strlen函数参数的部分需要传一个地址,当我们传递的是'a'时,'a'的ASCII码值是97,那就是将97作为地址传参。
//strlen就会从97这个地址开始统计字符串长度,这就非法访问内存了。

4、//错误

5、//&arr是数组的地址,数组的地址和数组首元素的地址,值是一样的,那么传递给strlen函数后,依然是从数组的第一个元素的位置开始往后统计。

6、//随机值

7、//&arr[0] + 1是第二个元素的地址。结果也是随机值。

字符串数组:

#include <stdio.h>int main()
{char arr[] = "abcdef";// a b c d e f \0printf("%d\n", sizeof(arr));//7printf("%d\n", sizeof(arr+0));//4printf("%d\n", sizeof(*arr));//1printf("%d\n", sizeof(arr[1]));//1printf("%d\n", sizeof(&arr));//4/8printf("%d\n", sizeof(&arr+1));//4/8printf("%d\n", sizeof(&arr[0]+1));//4/8return 0;
}

 解析: 

1、//7,类型是char [7]。

2、//arr + 0是首元素的地址。

3、//*arr其实就是首元素,1个字节,理解为*arr--> *(arr+0) -- arr[0]。

4、//arr[1]是第二个元素,1个字节。

5、//&arr是数组的地址,是地址就是4/8个字节。

6、//&arr + 1是跳过一个数组的地址,4/8。

7、//&arr[0] + 1是第二个元素的地址 4/8。

#include <stdio.h>int main()
{char arr[] = "abcdef";printf("%d\n", strlen(arr));//6printf("%d\n", strlen(arr+0));//6printf("%d\n", strlen(*arr));//错误printf("%d\n", strlen(arr[1]));//错误printf("%d\n", strlen(&arr));//6printf("%d\n", strlen(&arr+1));//随机值printf("%d\n", strlen(&arr[0]+1));//5return 0;
}

 解析: 

由于与上面内容相同,就不做过多解释

1、//6

2、//6

3、//err

4、//err

5、//6

6、//随机值

7、//5

一级指针: 

#include <stdio.h>int main()
{char *p = "abcdef";printf("%d\n", sizeof(p));//4/8printf("%d\n", sizeof(p+1));//4/8printf("%d\n", sizeof(*p));//1printf("%d\n", sizeof(p[0]));//1printf("%d\n", sizeof(&p));//4/8printf("%d\n", sizeof(&p+1));//4/8printf("%d\n", sizeof(&p[0]+1));//4/8return 0;
}

 解析: 

1、//p是一个指针变量,大小就是4/8。

2、//p+1是'b'的地址,是地址大小就是4/8个字节。

3、//*p 就是'a'元素,就是1个字节。

4、//p[0]--> *(p+0) --> *p  1个字节。

5、//4/8,类型是&p -- char**。

6、//4/8

7、//4/8 , &p[0] + 1得到是'b'的地址 。

#include <stido.h>int main()
{char *p = "abcdef";printf("%d\n", strlen(p));//6printf("%d\n", strlen(p+1));//5printf("%d\n", strlen(*p));//错误printf("%d\n", strlen(p[0]));//错误printf("%d\n", strlen(&p));//随机值printf("%d\n", strlen(&p+1));//随机值printf("%d\n", strlen(&p[0]+1));//5return 0;
}

 解析: 

由于与上面内容相同,就不做过多解释

1、//6

2、//5

3、//err

4、//err

5、//随机值

6、//随机值

7、//5

二维数组:

#include <stdio.h>int main()
{int a[3][4] = {0};printf("%d\n",sizeof(a));//48printf("%d\n",sizeof(a[0][0]));//4printf("%d\n",sizeof(a[0]));//16printf("%d\n",sizeof(a[0]+1));//4/8printf("%d\n",sizeof(*(a[0]+1)));//4printf("%d\n",sizeof(a+1));//4/8printf("%d\n",sizeof(*(a+1)));//16printf("%d\n",sizeof(&a[0]+1));//4/8printf("%d\n",sizeof(*(&a[0]+1)));//16printf("%d\n",sizeof(*a));//16printf("%d\n",sizeof(a[3]));//16return 0;
}

 解析: 

1、//3*4*4 = 48

2、//4

3、//a[0]是第一行这个一维数组的数组名,数组名算是单独放在sizeof内部了,计算的是整个数组的大小,大小是16个字节。

4、//a[0]作为第一行的数组名,没有单独放在sizeo内部,没有&,a[0]表示数组首元素的地址,也就是a[0][0]的地址,所以a[0]+1是第一行第二个元素的地址,是地址就是4/8个字节。

5、//4,计算的是就是第一行第2个元素的大小。

6、//4 / 8,a是数组首元素的地址,是第一行的地址 int(*)[4],a+1 就是第二行的地址。

7、//16,*(a+1) --> a[1] -> sizeof(*(a+1))->sizeof(a[1]) 计算的是第二行的大小,a+1 --> 是第二行的地址,int(*)[4],*(a+1) 访问的第二行的数组。

8、//4/8,&a[0]是第一行的地址 int(*)[4],&a[0]+1 是第二行的地址 int(*)[4]。

9、//16 计算的是第二行的大小。

10、//计算的是第一行的大小-16,a是数组首元素的地址,就是第一行的地址,*a 就是第一行,*a --> *(a+0) --> a[0]。

11、//16,类型是a[3]--> int [4]。

指针笔试题:

题一:一维数组

#include <stdio.h>int main()
{int a[5] = { 1, 2, 3, 4, 5 };int *ptr = (int *)(&a + 1);printf( "%d,%d", *(a + 1), *(ptr - 1));return 0;
}

注意:&a+1的类型为int( * )[ 5 ],强制转换为int( * ).此时每次移动的就是4个字节,而不是20个字节了!

题二: 结构体指针

#include <stdio.h>
//由于还没学习结构体,这里告知结构体的大小是20个字节
struct Test
{int Num;char *pcName;short sDate;char cha[2];short sBa[4];
}*p;
//假设p 的值为0x100000。 如下表表达式的值分别为多少?
//已知,结构体Test类型的变量大小是20个字节
int main()
{printf("%p\n", p + 0x1);printf("%p\n", (unsigned long)p + 0x1);printf("%p\n", (unsigned int*)p + 0x1);return 0;
}

注意:整型就是正常的加减运算指针类型就需要加减n*类型的大小。 

题三: 一维数组

#include <stdio.h>int main()
{int a[4] = { 1, 2, 3, 4 };int *ptr1 = (int *)(&a + 1);int *ptr2 = (int *)((int)a + 1);printf( "%x,%x", ptr1[-1], *ptr2);return 0;
}

注意: a强制转换成int类型+1就是正常加减,最后转换为指针int计算机会向后查找四个字节。

题四: 二维数组

#include <stdio.h>int main()
{int a[3][2] = { (0, 1), (2, 3), (4, 5) };int *p;p = a[0];printf( "%d", p[0]);return 0;
}

注意: 注意二维数组中没有用{ }把数值包含,这里用的是( )是逗号表达式取最后一个值为元素a[ 0 ]可以看做&a[ 0 ][ 0 ].

题五: 二维数组

#include <stdio.h>int main()
{int a[5][5];int(*p)[4];p = a;printf( "%p,%d\n", &p[4][2] - &a[4][2], &p[4][2] - &a[4][2]);return 0;
}

注意地址相减为相差的元素个数 ,此题为-4因为求的是地址,所以需要将-4转换成补码输出。

题六: 二维数组

#include <stdio.h>int main()
{int aa[2][5] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };int *ptr1 = (int *)(&aa + 1);int *ptr2 = (int *)(*(aa + 1));printf( "%d,%d", *(ptr1 - 1), *(ptr2 - 1));return 0;
}

注意:*(aa+1) = a[1] = &a[1][0]

题七:指针数组

#include <stdio.h>int main()
{char *a[] = {"work","at","alibaba"};char**pa = a;pa++;printf("%s\n", *pa);return 0;
}

注意:这里的a是指针数组,数组中每个位置的类型为char*。

题八: 指针数组(多级)

#include <stdio.h>int main()
{char *c[] = {"ENTER","NEW","POINT","FIRST"};char**cp[] = {c+3,c+2,c+1,c};char***cpp = cp;printf("%s\n", **++cpp);printf("%s\n", *--*++cpp+3);printf("%s\n", *cpp[-2]+3);printf("%s\n", cpp[-1][-1]+1);return 0;
}

注意:有了上面的基础,这道题一步一步来,你们也可以解释清楚!!!

以上就是个人学习见解和学习的解析,欢迎各位大佬在评论区探讨!

感谢大佬们的一键三连! 感谢大佬们的一键三连! 感谢大佬们的一键三连!

                                              

相关文章:

C语言:指针和数组(看完拿捏指针和数组)

目录 数组名的理解&#xff1a; 一维数组&#xff1a; 解析&#xff1a; 字符数组&#xff1a; 解析&#xff1a; 解析&#xff1a; 字符串数组&#xff1a; 解析&#xff1a; 解析&#xff1a; 一级指针&#xff1a; 解析&#xff1a; 解析&#xff1a; 二维数组&a…...

Conda命令整理-自用版

Conda用法整理-自用版 Conda介绍1、环境操作1.1 创建环境1.2 激活环境1.3 导出环境1.4 导入环境1.5 关闭环境1.6 删除环境 2、包操作2.1 安装软件包2.2 安装指定包的指定版本 参考资料 Conda介绍 Conda是一个开源的包管理系统和环境管理器&#xff0c;用于在不同的计算环境中安…...

CountDownLatch 和 CyclicBarrier的区别与详解

文章目录 一.CountDownLatch 和 CyclicBarrier的区别二.详解总结用法CountDownLatch 用法CyclicBarrier 用法 一.CountDownLatch 和 CyclicBarrier的区别 CountDownLatch和CyclicBarrier都是线程同步的工具类&#xff0c;都是基于AQS实现的&#xff1b;CountDownLatch 的计数器…...

Vue子组件向父组件传值(this.$emit()方法)

子组件使用this.$emit()向父组件传值 首先必须在父组件中引用子组件&#xff0c;然后实现传值 第一步 在父组件中引入子组件 使用import引入组件 import indexImportOrder from ./components/indexImportOrder 声明 //定义组件components:{indexImportOrder,}, 使用 &l…...

【C++】C/C++内存管理-new、delete

文章目录 一、C/C内存分布二、C/C中动态内存管理方式2.1 C语言中动态内存管理方式2.2 C内存管理方式 三、operator new和operator delete函数3.1 operator new和operator delete函数3.2 operator new与operator delete的类专属重载&#xff08;了解&#xff09; 四、new和delet…...

高手进阶之路---pyqt自定义信号

高手进阶之路—pyqt自定义信号 1.思考问题为什么要自定义信号&#xff0c;qt5本身已有信号槽函数 # pushButton 被clicked的时候connect 函数print self.pushButton.clicked.connect(self.print)def print(self):print("我被点击了")或者使用 # 需要引入 pyqtSlo…...

研磨设计模式day09原型模式

目录 场景 代码实现 有何问题 解决方案 代码改造 模式讲解 原型与new 原型实例与克隆出来的实例 浅度克隆和深度克隆 原型模式的优缺点 思考 何时选用&#xff1f; 相关模式 场景 代码实现 定义订单接口 package com.zsp.bike.day08原型模式;/*** 订单的接口*…...

(二)Redis——List

因为是 List&#xff0c;所以所有相关的命令都以 L 开头。 LPUSH / RPUSH LRANGE list 0 -1 -1 表示末尾 127.0.0.1:6379> LPUSH list a 1 127.0.0.1:6379> LRANGE list 0 -1 a 127.0.0.1:6379> LPUSH list b 2 127.0.0.1:6379> LRANGE list 0 -1 b a 127.0.0.…...

【Go Web 篇】Go 语言进行 Web 开发:构建高性能网络应用

随着互联网的快速发展&#xff0c;Web 开发已经成为了软件开发领域中不可或缺的一部分。随之而来的是对于更高性能、更高效的网络应用的需求。在这个领域&#xff0c;Go 语言因其并发性能、简洁的语法以及丰富的标准库而备受关注。本篇博客将深入探讨如何使用 Go 语言进行 Web …...

开悟Optimization guide for intermediate tracks

目录 认识模型 参考方案&#xff08;按模块拆解&#xff09; 认识模型 模型控制1名英雄进行镜像1 v 1对战 Actor集群资源为64核CPU 问题特点&#xff1a;单一公平对抗场景&#xff08;同英雄镜像对赛&#xff09;&#xff0c;单位时间样本产能低&#xff0c;累计训练资源相…...

wx.request配置服务器域名,只能包含英文大小写字母、数字,解决办法

前言.小程序服务器域名配置常见错误及解决方法 1.配置入口&#xff1a; 小程序后台->-开发->开发设置->服务器域名 2.常见错误及原因分析&#xff1a; 3.实战中出现的错误 4.解决办法&#xff1a;应把域名后边的路径去掉&#xff0c;只写域名即可...

【有效的括号】

题目 1、左括号入栈 2、右括号出栈顶括号进行匹配 栈 typedef char STDataType; //元素为char类型 typedef struct Stack {STDataType* a;//动态的开辟空间int top;int capacity; }ST;void StackInit(ST* ps)//初始化 {assert(ps);ps->a (STDataType*)malloc(sizeof(STD…...

积跬步至千里 || 数学基础、算法与编程

数学基础、算法与编程 1. BAP 技能 BAP 技能是指基础(Basic)、算法(Algorithm)和编程(Programm)三种基本技能的深度融合。理工科以数学、算法与编程为根基&#xff0c;这三个相辅相成又各有区别。 &#xff08;1&#xff09;数学以线性代数为主要研究工具和部分微积分技术为手…...

Java单元测试 JUnit 5 快速上手

一、背景 什么是 JUnit 5&#xff1f;首先就得聊下 Java 单元测试框架 JUnit&#xff0c;它与另一个框架 TestNG 占据了 Java领域里单元测试框架的主要市场&#xff0c;其中 JUnit 有着较长的发展历史和不断演进的丰富功能&#xff0c;备受大多数 Java 开发者的青睐。 而说到…...

【Linux网络】TCP UDP socket HTTP webSocket之间的区别

目录 一、OSI & TCP/IP模型 二、几者之间的关系 三、HTTP 四、Socket 五、WebSocket 5.1、WebSocket 优点 一、OSI & TCP/IP模型 首先我们要了解OSI七层模型&#xff0c;和预支对应的TCP/IP 四层的模型。 用下面的图可以看出&#xff0c;TCP UDP 工作在传输层&…...

【面向大一新生IT技术社群招新啦,不来瞅瞅?】

个人名片&#xff1a; &#x1f43c;作者简介&#xff1a;一名大三在校生 &#x1f43b;‍❄️个人主页&#xff1a;落798. &#x1f43c;个人WeChat&#xff1a;落798. &#x1f54a;️系列专栏&#xff1a;【零基础学java】 ----- 【重识c语言】 ---- 【计算机网络】—【Spri…...

分析系统 - 使用Python爬虫

在竞争激烈的市场环境中&#xff0c;了解和分析竞争对手的销售策略和市场表现对于企业的成功至关重要。本文将介绍如何利用Python爬虫建立低成本的销售竞争对手分析系统&#xff0c;探索其方法、工具和好处&#xff0c;并同时解决可能出现的问题。 销售竞争对手分析的目标是获取…...

strstr函数

目录 函数介绍&#xff1a; 函数分析&#xff1a; ​使用案例&#xff1a; 函数介绍&#xff1a; 返回指向 str1 中第一次出现的 str2 的指针&#xff0c;如果 str2 不是 str1 的一部分&#xff0c;则返回一个空指针。 匹配过程不包括终止空字符&#xff0c;但它到此为止。 …...

[C++] string类常用接口的模拟实现

文章目录 1、前言2、遍历2.1 operator[ ]下标方式2.2 迭代器2.3 范围for2.4 c_str 3、容量相关3.1 size&#xff08;大小&#xff09;3.2 capacity&#xff08;容量&#xff09;3.3 empty&#xff08;判空&#xff09;3.4 clear&#xff08;清理&#xff09;3.5 reserve3.6 res…...

每日一学——防火墙

防火墙是网络安全的重要组成部分&#xff0c;可以帮助保护网络免受恶意攻击和未经授权的访问。以下是防火墙的基本配置步骤&#xff1a; 定义安全策略&#xff1a;防火墙通过安全策略来决定允许或拒绝网络流量。你需要定义适当的安全策略来保护你的网络。安全策略通常包括源IP地…...

生成xcframework

打包 XCFramework 的方法 XCFramework 是苹果推出的一种多平台二进制分发格式&#xff0c;可以包含多个架构和平台的代码。打包 XCFramework 通常用于分发库或框架。 使用 Xcode 命令行工具打包 通过 xcodebuild 命令可以打包 XCFramework。确保项目已经配置好需要支持的平台…...

idea大量爆红问题解决

问题描述 在学习和工作中&#xff0c;idea是程序员不可缺少的一个工具&#xff0c;但是突然在有些时候就会出现大量爆红的问题&#xff0c;发现无法跳转&#xff0c;无论是关机重启或者是替换root都无法解决 就是如上所展示的问题&#xff0c;但是程序依然可以启动。 问题解决…...

从WWDC看苹果产品发展的规律

WWDC 是苹果公司一年一度面向全球开发者的盛会&#xff0c;其主题演讲展现了苹果在产品设计、技术路线、用户体验和生态系统构建上的核心理念与演进脉络。我们借助 ChatGPT Deep Research 工具&#xff0c;对过去十年 WWDC 主题演讲内容进行了系统化分析&#xff0c;形成了这份…...

模型参数、模型存储精度、参数与显存

模型参数量衡量单位 M&#xff1a;百万&#xff08;Million&#xff09; B&#xff1a;十亿&#xff08;Billion&#xff09; 1 B 1000 M 1B 1000M 1B1000M 参数存储精度 模型参数是固定的&#xff0c;但是一个参数所表示多少字节不一定&#xff0c;需要看这个参数以什么…...

深入浅出:JavaScript 中的 `window.crypto.getRandomValues()` 方法

深入浅出&#xff1a;JavaScript 中的 window.crypto.getRandomValues() 方法 在现代 Web 开发中&#xff0c;随机数的生成看似简单&#xff0c;却隐藏着许多玄机。无论是生成密码、加密密钥&#xff0c;还是创建安全令牌&#xff0c;随机数的质量直接关系到系统的安全性。Jav…...

Nuxt.js 中的路由配置详解

Nuxt.js 通过其内置的路由系统简化了应用的路由配置&#xff0c;使得开发者可以轻松地管理页面导航和 URL 结构。路由配置主要涉及页面组件的组织、动态路由的设置以及路由元信息的配置。 自动路由生成 Nuxt.js 会根据 pages 目录下的文件结构自动生成路由配置。每个文件都会对…...

全志A40i android7.1 调试信息打印串口由uart0改为uart3

一&#xff0c;概述 1. 目的 将调试信息打印串口由uart0改为uart3。 2. 版本信息 Uboot版本&#xff1a;2014.07&#xff1b; Kernel版本&#xff1a;Linux-3.10&#xff1b; 二&#xff0c;Uboot 1. sys_config.fex改动 使能uart3(TX:PH00 RX:PH01)&#xff0c;并让boo…...

虚拟电厂发展三大趋势:市场化、技术主导、车网互联

市场化&#xff1a;从政策驱动到多元盈利 政策全面赋能 2025年4月&#xff0c;国家发改委、能源局发布《关于加快推进虚拟电厂发展的指导意见》&#xff0c;首次明确虚拟电厂为“独立市场主体”&#xff0c;提出硬性目标&#xff1a;2027年全国调节能力≥2000万千瓦&#xff0…...

Git常用命令完全指南:从入门到精通

Git常用命令完全指南&#xff1a;从入门到精通 一、基础配置命令 1. 用户信息配置 # 设置全局用户名 git config --global user.name "你的名字"# 设置全局邮箱 git config --global user.email "你的邮箱example.com"# 查看所有配置 git config --list…...

Proxmox Mail Gateway安装指南:从零开始配置高效邮件过滤系统

&#x1f49d;&#x1f49d;&#x1f49d;欢迎莅临我的博客&#xff0c;很高兴能够在这里和您见面&#xff01;希望您在这里可以感受到一份轻松愉快的氛围&#xff0c;不仅可以获得有趣的内容和知识&#xff0c;也可以畅所欲言、分享您的想法和见解。 推荐&#xff1a;「storms…...