数组和指针的区别

合集下载

专题7 数组和指针的应用

专题7  数组和指针的应用

例1. 写出结果: main() { int *p1, a[10]={1,2,3,4,5,6,7,8,9,10} ; p1=a; printf(“%d ”,*p1); printf(“%d ”,*p1++); printf(“%d ”, *(p1+3)); printf(“%d ”,*++p1); printf(“%d ”,(*p1)++); printf(“%d ”,*p1--); printf(“%d ”,*p1); } 例2.若有定义语句:double x[5]={1.0,2.0,3.0,4.0,5.0},*p=x;则错误引用x数 组元素的是[08年9月] A)*p B)x[5] C)*(p+1) D)*x
[C] D) aa+1
(3)通过指针变量来表示数组中各元素的地址
可以定义一个指针变量来存放数组的指针或数组元素的指针,且指针变 量的基类型就是定义数组时的类型 int *p,a[10]; for(p=a,k=0; k<10;k++) p++; 将数据写入数组元素中几种方式: (1)for(p=a,k=0; k<10;k++) { scanf(“%d”,p); p++; } 进一步简化: (2)for(p=a,k=0; k<10;k++) scanf(“%d”,p++); 再进一步简化: (3)for(p=a,p-a<10; p++) scanf(“%d”,p); 以上三种写法是等价的,要掌握,能看懂。
2、 通过指针变量来引用一维数组元素 当指针变量指向数组中的某个数组元素时,可以通过“*”来访问其所 指向变量的数据。

指针和数组的关系

指针和数组的关系

指针和数组的关系
指针和数组是C语言中非常重要的概念,理解它们对于编写高效程序和避免常见错误
至关重要。

指针和数组的关系可以说是紧密相连的,因为数组名本质上就是一个指针。

在C语言中,数组名表示一个指向该数组第一个元素的指针,也就是数组的起始地址。

因此,如果我们定义一个数组a,那么&a和a是等价的,都表示数组第一个元素的地址。

例如,定义一个整型数组a:
int a[5] = {1, 2, 3, 4, 5};
我们可以通过数组名a访问数组中的元素。

例如,a[0]表示数组中的第一个元素,即1。

在C语言中,数组名本身是一个常量,即不能对其进行修改。

但是,我们可以使用指
针来访问数组中的元素,这就需要对指针进行加减运算来实现。

我们可以定义一个指向数组a的指针p,然后通过指针访问数组中的元素。

例如,*p
表示指针p所指向的数组的第一个元素,即1。

我们可以通过p++将指针p指向数组中的下一个元素,例如*p++表示指向数组中的第二个元素,即2。

因此,数组名和指针在C语言中是紧密相关的,数组名本质上就是一个指向数组第一
个元素的指针。

我们可以通过指针访问数组中的元素,并通过加减运算实现对数组的遍
历。

在实际编程中,使用指针可以提高程序的效率和灵活性。

使用指针可以避免对数组名
的重复引用,从而减少程序的存储空间和运行时间开销。

但是,指针操作也比较容易出现指针越界、空指针等错误,因此在使用指针时需特别
注意,避免出现不必要的错误。

数组和指针的区别

数组和指针的区别

数组和指针的区别数组和指针是C语言中非常重要的两个概念,它们在编写程序时起着极其重要的作用。

虽然它们在某种程度上非常相似,但它们之间也存在着很多的差异,下面我们就来分析一下它们的区别。

1. 定义方式数组是由一组具有相同类型的数据元素所组成的有序集合,每个元素具有相同的数据类型,可以通过下标在数组中访问对应的元素。

在C中,定义一个数组可以使用以下语句:```int arr[10];```这个语句定义了一个名为arr的整型数组,这个数组有10个元素。

而指针是一个变量,它存放了一个内存地址,这个地址与它存储的数据类型有关。

在C中,定义一个指针可以使用以下语句:```int *p;```这个语句定义了一个名为p的指针,这个指针指向一个整型变量。

2. 内存分配数组在定义时要求需要一定的内存空间来存储数组元素,因此在定义时就已经确定了内存空间的大小,且数组的大小不可改变。

例如,如果定义一个大小为10的数组,则它的大小就是10,无论实际使用时需要存储的元素个数是多少,数组的大小都不会改变。

而指针在定义时只需要分配一个指针变量所需的内存空间,该指针可以在程序运行时动态地分配内存,因此指针所指向的内存空间大小不确定,需要在运行时根据需要动态地分配或释放空间。

3. 访问方式在数组中,可以通过数组的下标来访问数组中具体的元素,下标从0开始,最大下标为数组大小减1。

例如,访问arr数组中的第三个元素可以写成:arr[2]。

而对于指针,可以通过指针变量所指向的地址来访问该地址所对应的值。

例如,访问p指针所指向地址上的整型变量可以写成:*p。

4. 传递方式在函数调用时,数组可以通过值传递或指针传递来传递数组的值。

如果数组作为参数传递给函数时,实际上传递的是该数组的地址,即使数组非常大,也不会导致栈溢出。

而对于指针,只能通过指针传递方式来传递指针变量的值,在函数内部可以通过指针来修改该指针所指向的地址所存储的值,因此指针可以用来传递地址或修改变量的值。

用指针访问数组的方法

用指针访问数组的方法

用指针访问数组的方法一、指针与数组的关系。

1.1 指针就像是数组的导航员。

数组在内存里是一块连续的空间,就像住在公寓里的一排房间。

而指针呢,就好比是房间的钥匙或者说是指向这些房间的路标。

它能准确地找到数组里的每个元素,这就跟你拿着钥匙能打开对应的房间门一样。

咱们可以把数组想象成一群小伙伴排着队,指针就可以指出哪个是排头,哪个是排尾,还能找到中间的小伙伴。

1.2 从本质上来说,数组名其实就是一个指针常量。

这就像是一个固定的地址标签,它指向数组的第一个元素。

就好比你家的门牌号,永远指着你家这个“元素”所在的位置。

而且,这个指针常量是不能被修改的,就像你不能随便更改你家的门牌号一样。

二、用指针访问数组元素。

2.1 简单的访问方式。

咱们先定义一个数组,比如说int arr[5] = {1, 2, 3, 4, 5};再定义一个指针,int p = arr; 这里的arr就相当于把数组的首地址给了指针p。

现在如果我们想访问数组的第一个元素,就可以用p,这就像是通过钥匙打开了第一个房间。

如果我们想访问第二个元素呢,那就可以让指针p指向下一个元素,也就是p++,然后再用p来获取这个元素的值。

这就好像你沿着走廊走到下一个房间,再用钥匙打开门看看里面有啥。

2.2 灵活的遍历。

通过指针来遍历数组那是相当方便的。

我们可以写一个简单的循环,像这样:for (int p = arr; p < arr + 5; p++) { printf("%d ", p); }。

这个循环就像是一个小机器人,从数组的开头沿着指针这个“导航路线”一直走到结尾,把每个房间里的东西(元素的值)都展示出来。

这就好比是你沿着一排房间一个一个地查看里面的情况,一个都不落下。

2.3 指针运算的妙处。

指针的运算在访问数组的时候可是很有讲究的。

比如说,p + 2,这里可不是简单的数学加法,它实际上是让指针向后移动两个元素的位置。

这就像是你一下子跳过两个房间,直接到第三个房间的门口。

字符串指针与字符数组的区别

字符串指针与字符数组的区别

字符串指针与字符数组的区别(转载)用字符数组和字符指针变量都可实现字符串的存储和运算。

但是两者是有区别的。

在使用时应注意以下几个问题:1. 字符串指针变量本身是一个变量,用于存放字符串的首地址。

而字符串本身是存放在以该首地址为首的一块连续的内存空间中并以‘\0’作为串的结束。

字符数组是由于若干个数组元素组成的,它可用来存放整个字符串。

2. 对字符串指针方式char *ps="C Language";可以写为:char *ps;ps="C Language";而对数组方式:static char st[]={"C Language"};不能写为:char st[20];st={"C Language"};而只能对字符数组的各元素逐个赋值。

从以上几点可以看出字符串指针变量与字符数组在使用时的区别,同时也可看出使用指针变量更加方便。

当一个指针变量在未取得确定地址前使用是危险的,容易引起错误。

一个错误的例子,如下:char *name;scanf("%s",name);printf("%s",name);有的编译器虽然也能通过,但这是错误的,因为是个指针,定义时指向不可用的地址。

解决这个问题有两种方法:用数组的方法或给字符针针分配内存空间的方法。

数组的方法:char name[20];scanf("%s",name);printf("%s",name);给字符针针分配内存空间的办法:char *name;name=(char*)malloc(50);//此时name已经指向一个刚刚分配的地址空间。

scanf("%s",name);printf("%s",name);但是对指针变量直接赋值是可以的。

因为C系统对指针变量赋值时要给以确定的地址。

理解C语言(一)数组、函数与指针

理解C语言(一)数组、函数与指针

理解C语⾔(⼀)数组、函数与指针1 指针⼀般地,计算机内存的每个位置都由⼀个地址标识,在C语⾔中我们⽤指针表⽰内存地址。

指针变量的值实际上就是内存地址,⽽指针变量所指向的内容则是该内存地址存储的内容,这是通过解引⽤指针获得。

声明⼀个指针变量并不会⾃动分配任何内存。

在对指针进⾏间接访问前,指针必须初始化: 要么指向它现有的内存,要么给它分配动态内存。

对未初始化的指针变量执⾏解引⽤操作是⾮法的,⽽且这种错误常常难以检测,其结果往往是⼀个不相关的值被修改,并且这种错误很难调试,因⽽我们需要明确强调: 未初始化的指针是⽆效的,直到该指针赋值后,才可使⽤它。

 int *a;*a=12; //只是声明了变量a,但从未对它初始化,因⽽我们没办法预测值12将存储在什么地⽅int *d=0; //这是可以的,0可以视作为零值int b=12;int *c=&b;另外C标准定义了NULL指针,它作为⼀个特殊的指针常量,表⽰不指向任何位置,因⽽对⼀个NULL指针进⾏解引⽤操作同样也是⾮法的。

因⽽在对指针进⾏解引⽤操作的所有情形前,如常规赋值、指针作为函数的参数,⾸先必须检查指针的合法性- ⾮NULL指针。

解引⽤NULL指针操作的后果因编译器⽽异,两个常见的后果分别是返回置0的值及终⽌程序。

总结下来,不论你的机器对解引⽤NULL指针这种⾏为作何反应,对所有的指针变量进⾏显式的初始化是种好做法。

如果知道指针被初始化为什么地址,就该把它初始化为该地址,否则初始化为NULL在所有指针解引⽤操作前都要对其进⾏合法性检查,判断是否为NULL指针,这是⼀种良好安全的编程风格1.1 指针运算基础在指针值上可以进⾏有限的算术运算和关系运算。

合法的运算具体包括以下⼏种: 指针与整数的加减(包括指针的⾃增和⾃减)、同类型指针间的⽐较、同类型的指针相减。

例如⼀个指针加上或减去⼀个整型值,⽐较两指针是否相等或不相等,但是这两种运算只有作⽤于同⼀个数组中才可以预测。

数组与指针

数组与指针

此外,还可通过算术元运算对指针进行移动, 此外,还可通过算术元运算对指针进行移动,来达到引用 其他数组元素的目的。 其他数组元素的目的。 a[0] p p &a[0] *p a[0] a[1] p+1 p+1 &a[1] *(p+1) a[1] a[2] P+2 p+2 &a[2] *(p+2) a[2] a[3] P+3 p+3 &a[3] *(p+3) a[3] a[4] p+4 p+4 &a[4] *(p+4) a[4]
a[0] a[1] a[2] a[3] a[4]
a
a a+1 a+2 a+3 a+4
a a+1 a+2 a+3 a+4
&a[0] &a[1] &a[2] &a[3] &a[4]
*a *(a+1) *(a+2) *(a+3) *(a+4)
a[0] a[1] a[2] a[3] a[4]
例3: main() { int a[5],*p,i; for(i=0;i<5;i++) scanf(“%d”,a+i); for(i=0;i<5;i++) printf(“%d”,*(a+i)); }
a[1] a[1][0] a[1][1] a[1][2]
此处, 的值与 的值与a[0]的值相同,但是基类型不同。a是二级 的值相同, 此处,a的值与 的值相同 但是基类型不同。 是二级 指针, 是一级指针。 指针,a[0]是一级指针。 是一级指针 a &a[0][0] a[0] 因此,以下赋值语句是错误的: 因此,以下赋值语句是错误的:p=a; a &a[0] a+1 &a[1] a+i &a[i] *(a+i) a[i]

字符串指针和字符数组,静态全局、静态局部、全局和局部变量区别,字符串常量和字符串变量,程序的内存分配

字符串指针和字符数组,静态全局、静态局部、全局和局部变量区别,字符串常量和字符串变量,程序的内存分配

最近工作之余,发现了两个自己在C语言学习中的难点,一个是字符串指针和字符数组的区别,一个就是静态全局变量、静态局部变量、全局变量和局部变量的区别,在网上查了不少资料,收获良多,现在与大家分享,有错误的地方请大家指正!以下程序用VC++6.0调试先说说字符串指针和字符数组的区别1.相同点:/* 用字符数组实现字符串操作*/main( ){char str[]="Welcome to study C !";int i;printf("%s\n",str);for (i=0;i<=7;i++)printf("%c",str[i]); //用*(str+i)也行printf("\n");}/* 用字符指针实现字符串操作*/main(){char *str="Welcome to study C !";int i;printf("%s\n",str);for(i=0;i<=7;i++)printf("%c",*(str+i)); //用str[i]也行printf("\n");}2.不同点:a)赋值方式不同,字符数组只能对各个元素分别赋值,而字符指针只需赋给字符串的首地址就可以了。

如: char *str;str="Welcome to study C !";以下对字符数组的赋值是错误的:char str[80];str[ ]="Welcome to study C !";b)字符指针指向字符串,"hello"是一个字符串常量,与之相关联的内存空间位于内存的只读部分,如:char ch[] = "china\n";char *p;char *pp = "CHINA\n";p = ch;*(p+2) = 'h';//就是可以的*(pp+2) = 'h';//此处在编译时不会出错,在执行的时候会出错c) 函数参数列表中的以数组类型书写的形式参数,编译器把其解释为普通的指针类型,对于void func (char sa[100],int ia[20],char *p),则sa的类型为char*,而不是char[100]类型下面介绍一下字符串常量和字符串变量:1.字符串常量:a)定义:是一对双引号括起来的字符序列b)字符串包含的字符个数:不包括系统自动赋的’\0’,转义字符算1个c)所占的字节数:字符串所包含的字符个数加1d)长度:从第一个字符到第一个’\0’之间的字符个数,哪怕’\0’就在原字符串中e)无论字符串常量还是字符串变量,空字符串可以存在””,而空字符是错误的’’2.字符串变量:a)C语言本身没有设置一种类型来定义字符串变量,字符串的存储完全依赖于字符数组,但字符数组又不等于是字符串变量,例如:Char str[] = {‘a’,’b’,’c’,’\0’};是str[4],是字符串Char str[] = {‘a’,’b’,’c’};是str[3],是字符数组Char str[7] = “string!”;可能破坏其他数据b)在scanf,printf,gets,puts中的str不用写成str[10],只能写成str下面介绍下静态全局变量,静态局部变量,全局变量,局部变量的区别1.从作用域看:全局变量具有全局作用域。

  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
计算出数组的容量(字 节数)。(包括最后面的'\0')。指针p指向a, 但是sizeof(p)的值却是4。这是因为sizeof(p)得 到的是一个指针变量的字节数,相当于 sizeof(char*),而不是p所指的内存容量 siziof(char[6])。C++/C不能知道指针所指的内 存容量。 值得注意的是,当数组作为函数的参数进 行传递时,数组就自动退化为同类型的指针。 那么不论数组a的容量是多少,sizeof(a)始终等 于sizeof(char *)。

char str[7]=”ksarea”; char *pstr=str; cout<< str[3]<<pstr[3]<<endl; 其中str[3]和pstr[3]返回的都是字符‟r„,但是编译 器产生的执行代码却不一样。对于str[3],执行代 码是从str开始,向后移动三个字节,然后取出其中 的字符;而对于pstr[3],执行代码是从pstr中取出 地址,然后在其上加3,然后取出对应内存中的字 符。当然,如果pstr是指向int型的指针,那么 pstr[3]的处理过程是从pstr中取出地址,然后在其 上加上3*sizeof(int),最后取出对应内存中的字符, 其他的数据类型一次类推。

a. 将数组名直接赋值给指针,数组名转换为指 向数组的首单元的常量指针。 b.直接将数组名作为指针形参的时候,数组名 则转换为指向数组的首单元的常量指针进行传 递,如下程序2: void fun(char str[]) 。。。 char str1[5]; fun(str1);
数组名作为函数形参进行传递时,在子函数体
内,它已经不再是一个指针常量,而是变成一 个真正的指针,可以进行增减等操作,可以被 修改。所以程序2中子程序第一条语句输出的 sizeof(str)的值为4.
既然数组名可以被看作指针常量,而常量是不
能修改的,那么如下代码是不允许的: char str[10]; str++; 但如下代码则合法的: char str[10]; char *pstr=str; pstr++;
数组或是在静态存储区被创建(全局数 组),或是在栈上被创建。数组名对应着,注 意不是指向,一块内存,其地址与容量在生命 期内保持不变(当然,使用了realloc()的不 算),只有数组的内容可以改变。 指针可以随时指向任意类型的内存块,它 的特征是“可变”,所以我们常用指针来操作动 态内存。指针远比数组灵活,当然也就更危险。

char
str[10]; char *pstr=str; cout<<sizeof(str); cout<<sizeof(pstr); 第一行输出结果是:10,第二行输出结果是: 4
数组名对应着(而不是指向)一块内存(数组
所占的内存区域)或者说是指代数组这种数据 结构,其地址与容量在生命期内保持不变,只 有数组的内容可以改变。指针对应着一个占据4 个字节(Win32)的内存区域,而指向这4个字 节所存储的地址所对应的内存单元,它可以指 向任意类型的内存块。因此,sizeof(str)值为数 组占据的内存空间大小即10个字节,而 sizeof(pstr)值为指针的值占据的内存空间大小 即4个字节。
相关文档
最新文档