c语言指针,如何让脑笨的人理解c语言指针和函数?
看我的抖音短视频,里面非常通俗的讲解了 指针,函数!
脑笨的人也很轻松的理解!
c语言指针的6个用处?
C 语言中指针的作用非常广泛,下面列举了一些主要的用途:
动态内存分配:通过指针,可以在程序运行过程中动态地分配和释放内存。这使得内存使用更加灵活,允许创建大小可变的数据结构,如链表、树、图等。
数组操作:指针可以用于操作数组元素。通过使用指针,可以更高效地遍历数组、传递数组给函数或从函数返回数组。
传递引用参数:通过指针,可以将变量的地址传递给函数。这样,在函数内部就可以通过指针直接修改实参的值,而不仅仅是局部的形参。这种方法可以实现多个返回值,也可以提高函数参数传递的效率。
实现数据结构:指针在实现高级数据结构时非常有用,例如链表、树、图等。这些数据结构通常包含指向其他元素或节点的指针,以表示它们之间的关系。
函数指针:通过函数指针,可以将函数作为参数传递给其他函数,实现回调函数、策略模式等高级编程技巧。函数指针还可以用于构建函数查找表,实现快速的函数调用。
操作底层数据:指针可以用于直接访问和操作计算机内存中的数据,这在底层编程、硬件编程或操作系统开发等领域非常重要。通过指针,可以实现内存拷贝、内存映射等底层操作。
C语言里的指针是干什么的?
指针,是C语言中的一个重要概念及其特点,也是掌握C语言比较困难的部分。指针也就是内存地址,指针变量是用来存放内存地址的变量,在同一CPU构架下,不同类型的指针变量所占用的存储单元长度是相同的,而存放数据的变量因数据的类型不同,所占用的存储空间长度也不同。
有了指针以后,不仅可以对数据本身,也可以对存储数据的变量地址进行操作。
C语言中怎么理解野指针?
C语言的指针是本分之九十初学者最难过的一关,因为它比较抽象。想要去理解和熟练运用指针就少不了从原理层去认识它。这里小编就自己学习指针过程中的一些理解,总结出来分享给您;
理解指针首先,你需要掌握两个运算符“*”和“&”;
“&”运算符:取对象在内存中的地址
“*”运算符:取内存中地址上的对象(值);
大家一定要深刻的理解上面两个运算符,然后才能去进一步理解指针;
int a = 100 ;这一行代码我想大家都没问题。那么“&a”返回的就是对象(变量)a在内存中的地址,它是一个16进制数。
然后用“*”号去a的地址去取对象:“*(&a)”,,就能取到对象a,也就就是100 ;
接下来进入重点了,指针,本身也是一个变量(对象),它本身占用内存,但是它只存地址(别人的地址),它存的谁的地址我们就称它为指向谁的指针;
int* p = &a ;int* p_2 = new int(200) ;先不管他的类型申明,只看变量本身p和p_2。前面讲到指针存放的是对象的地址,那么可以理解为指针是一个地址变量,那么赋值的话就需要也赋一个地址给它一个地址。int* 和char*都可以表示地址类型,它们的区别就是地址所存的值得类型不同,一个是存整型,一个是存字符型;
对指针取值的话,就是用“*”号,后面接对象地址,也就是指针变量,所以*p和*p_2就分别是a和200;
指针的运用指针并不是C/C++独有的,像C#和java等其实也是有指针的,只不过都被语言本身用其他的方式替代和封装了一般程序员接触不到,C/C++就不一样,它是直接将指针暴露给开发者,因为大部分牵涉到指针的都与内存有关,而计算机内存很重要,万一出什么问题可能系统都会崩溃,下面就简单来看一下程序在运行时指针与内存之间到底是个什么样的关系:
先看一段代码:
#include <stdio.h>#include <string>#include <iostream>#include <time.h>using namespace std;class people{public:people();~people();string Name ;int age ;bool sex ;char info[1024] ;void run(){}void eat(){}private:};people::people(){}people::~people(){}int main(){people* p1 = new people();cout<<p1<<endl;cout<<&p1<<endl;cout<<sizeof(p1)<<endl;cout<<sizeof(*p1)<<endl;system("pause");return 0 ;}直接运行看结果:
分析接下来来一一进行分析:
首先people* p1 = new people();这一句是类的一个实例化,系统会给people实例化一个对象*p并且给它在堆上开辟空间,注意是在堆上,开辟的空间用来存储对象的数据。数据包括哪些?就是对象的属性和虚函数指针,但是函数并不存储在各对象中。因此run()和eat()方法是不存在对象*p指向的内存处的。
cout<<p1<<endl;输出的是00279360,这是一个地址,是系统给new people()对象分配的地址。
cout<<&p1<<endl;输出的是0012FD90,这也是地址,但这是指针变量p本身的地址。
cout<<sizeof(p1)<<endl;
cout<<sizeof(*p1)<<endl;
通过这两个输出就能有更清晰的认识了,p1本身只占用4个字节的空间,而它所指向的对象的地址所占的空间就很大,等于类中所有数据类型所占空间之和。
接下来在main函数里写一点逻辑:
图解我们来看一下程序运行时间,指针和内存是怎么工作的。这里画一个图给大家:
程序在运行时,数据主要是存储在栈、堆、代码区、全局区。代码区主要就是存代码中出现的一些字符常量、方法等,比如这里代码中给对象的Name属性赋的值“xiaoli”之类的都是存在此处,然后我们通过new出来的对象,都是由堆通过计算好类中各属性所需空间然后开辟出来的。这里p3不是通过new开辟出来的,所以他是存在栈上的并且地址是固定的,是不能更改的,而p1和p2是能更改的。
改变地址
如此,我们三个对象互相赋值后会发生什么呢?
对比代码和输出结果我们发现了什么?赋值后p1和p2本身的地址并无改变,但是他所指向的内存都编程p3所在的内存了。下面用图解给大家看一下:
注意,此处原来的p1和p2指向的内存由于是new出来的我们需要手动释放它。所以我们在重新赋值之前要将这两块内存删除掉delete p2 ;delete p1;
改变地址的值
如果我将代码中的 p2 = &p3;换成*p2=p3呢?我们看下输出结果:
造成这种情况的原因,其实这就牵涉到指针的两种赋值问题:一种是改变指向的地址,一种是改变本身指向地址的值p2 = &p3是改变指向地址,*p2=p3是改变指向地址的值。
c语言的修饰指针有哪些?
typedef
用于给某个数据类型定义一个新的名字。
如:
typedef int32 ac_int32;
typedef struct _student_st {
int age;
char* pName;
} student_st;
2. extern
引用另一个文件中的函数或全局变量。注意,这些函数和变量是不能被static修饰的。
如:
extern int otherInt;
3. static
被修饰的函数和变量,只能在当前的文件中使用。当static修改局部成员变量时,该变量只会被初始化一次,直到进程结束,才会被销毁。被static修饰的变量将会被保存在全局数据区的静态变量部分。
如:
static int glbInt;
4. _Thread_local (C++中会使用到)
5. auto
表示自动存储的临时变量,也用作自动匹配变量的数据类型。
如:
auto int var = 4;
auto var1 = 0;
6. register
寄存器变量,说明该变量的使用频率非常高,希望编译器尽量将它放到寄存器中。当然,编译器也可以将它忽略。
使用这个修饰符,需要注意:
变量需要是CPU能接受的类型,即单个值,长度小于整型。
只能用到局部变量或函数形参。
不能使用&来引用该变量的地址。
过量的寄存器变量不会对代码产生太大的影响,编译器是可以忽略的。
还没有评论,来说两句吧...