C/C++ 指针变量

一、指针变量

C 指针
每一个变量都有一个内存位置,每一个内存位置都定义了可使用连字号(&)运算符访问的地址,它表示了在内存中的一个地址。
指针变量的值是具有实际值的变量的内存地址,普通变量的值是实际的值;使用 * 来访问该地址上的变量。

如果指针被定义为const:一旦得到了某个变量的地址,不能再指向其他变量(指针是const);判断const在*前还是 *后。

int  *const q = &i;// q是const,q指向的这个地址,不能再改变;
*q = 26;// OK ,此时i = 26
q++;   // ERROR

所指是const:不能通过这个指针取修改那个变量;并不是使那个变量变成const

const  int  *q = &i;// *q是const,不能通过*q去改变i的值;
*q = 26;// ERROR ,此时(*q)是const
i = 26;//OK
q++;   //OK 

动态内存分配:
malloc返回的是分配的这段内存的首地址;类似于返回了一个数组的首地址;

malloc 函数定义:
void * malloc(size_t size);

#include <stdlib.h>   //  头文件
 
 int  *a;
  a = (int *)malloc(number*sizeof(int));//malloc返回void * 类型,使用int * 进行类型转换
  ....
  free(a);

函数malloc()和calloc()都可以用来动态分配内存空间,但两者稍有区别。

malloc()函数有一个参数,即要分配的内存空间的大小:

void *malloc(size_t size);

calloc()函数有两个参数,分别为元素的数目和每个元素的大小,这两个参数的乘积就是要分配的内存空间的大小。

void *calloc(size_t numElements,size_t sizeOfElement);

如果调用成功,函数malloc()和函数calloc()都将返回所分配的内存空间的首地址。

函数malloc()和函数calloc()的主要区别是前者不能初始化所分配的内存空间,而后者能。如果由malloc()函数分配的内存空间原来没有 被使用过,则其中的每一位可能都是0;反之,如果这部分内存曾经被分配过,则其中可能遗留有各种各样的数据。也就是说,使用malloc()函数的程序开 始时(内存空间还没有被重新分配)能正常进行,但经过一段时间(内存空间还已经被重新分配)可能会出现问题。

函数calloc()会将所分配的内存空间中的每一位都初始化为零,也就是说,如果你是为字符类型或整数类型的元素分配内存,那麽这些元素将保证会被初始 化为0;如果你是为指针类型的元素分配内存,那麽这些元素通常会被初始化为空指针;如果你为实型数据分配内存,则这些元素会被初始化为浮点型的零。

实例:
#include <stdio.h>

int main ()
{
int var1;
char var2[10];

printf(“var1 变量的地址: %p\n”, &var1 );
printf(“var2 变量的地址: %p\n”, &var2 );

return 0;
}


当上面的代码被编译和执行时,它会产生下列结果:

var1 变量的地址: 0x7fff5cc109d4
var2 变量的地址: 0x7fff5cc109de
通过上面的实例,我们了解了什么是内存地址以及如何访问它。接下来让我们看看什么是指针。

什么是指针?
指针是一个变量,其值为另一个变量的地址,即,内存位置的直接地址。就像其他变量或常量一样,您必须在使用指针存储其他变量地址之前,对其进行声明。指针变量声明的一般形式为:

type *var-name;


在这里,type 是指针的基类型,它必须是一个有效的 C 数据类型,var-name 是指针变量的名称。用来声明指针的星号 * 与乘法中使用的星号是相同的。但是,在这个语句中,星号是用来指定一个变量是指针,*是一个运算符,用来取出它右边的那个指针所指的变量。以下是有效的指针声明:

int ip; / 一个整型的指针 */
double dp; / 一个 double 型的指针 */
float fp; / 一个浮点型的指针 */
char ch; / 一个字符型的指针 */

所有实际数据类型,不管是整型、浮点型、字符型,还是其他的数据类型,对应指针的值的类型都是一样的,都是一个代表内存地址的长的十六进制数。

不同数据类型的指针之间唯一的不同是,指针所指向的变量或常量的数据类型不同。

如何使用指针?
使用指针时会频繁进行以下几个操作:定义一个指针变量、把变量地址赋值给指针、访问指针变量中可用地址的值。这些是通过使用一元运算符 * 来返回位于操作数所指定地址的变量的值。下面的实例涉及到了这些操作:

实例

#include <stdio.h>

int main ()
{
int var = 20; /* 实际变量的声明 */
int ip; / 指针变量的声明 */

ip = &var; /* 在指针变量中存储 var 的地址 */

printf(“Address of var variable: %p\n”, &var );

/* 在指针变量中存储的地址 */
printf(“Address stored in ip variable: %p\n”, ip );

/* 使用指针访问值 */
printf(“Value of *ip variable: %d\n”, *ip );

return 0;
}


当上面的代码被编译和执行时,它会产生下列结果:

Address of var variable: bffd8b3c
Address stored in ip variable: bffd8b3c
Value of *ip variable: 20


C 中的 NULL 指针
在变量声明的时候,如果没有确切的地址可以赋值,为指针变量赋一个 NULL 值是一个良好的编程习惯。赋为 NULL 值的指针被称为空指针。

NULL 指针是一个定义在标准库中的值为零的常量。请看下面的程序:

实例

#include <stdio.h>

int main ()
{
int *ptr = NULL;

printf(“ptr 的地址是 %p\n”, ptr );

return 0;
}


当上面的代码被编译和执行时,它会产生下列结果:

ptr 的地址是 0x0
在大多数的操作系统上,程序不允许访问地址为 0 的内存,因为该内存是操作系统保留的。然而,内存地址 0 有特别重要的意义,它表明该指针不指向一个可访问的内存位置。但按照惯例,如果指针包含空值(零值),则假定它不指向任何东西。

如需检查一个空指针,您可以使用 if 语句,如下所示:

if(ptr) /* 如果 p 非空,则完成 /
if(!ptr) /
如果 p 为空,则完成 */


下面的实例演示了 strchr() 函数的用法。

#include <stdio.h>
#include <string.h>

int main ()
{
const char str[] = “http://www.runoob.com”;
const char ch = ‘.’;
char *ret;

ret = strchr(str, ch);

printf("|%c| 之后的字符串是 - |%s|\n", ch, ret);

return(0);
}


让我们编译并运行上面的程序,这将产生以下结果:
|.| 之后的字符串是 - |.runoob.com|

字符指针变量,可以采用下面方法赋值:

char *a;
a="hello";


指针变量指向的字符串内容不能被修改:
例一:指针变量指向的字符串内容不能被修改

char *p = "hello"; //字符指针指向字符串常量
*p = 'a'; //错误,常量不能被修改,即指针变量指向的字符串内容不能被修改
说明:定义一个字符指针指向字符串常量“hello”,修改指针变量指向的字符串的内容,即*p = 'a',发生错误,指针变量指向字符串常量,而常量字符串存在文字常量区,这段空间中的内容为只读内容,不能被修改,即指针变量指向的字符串内容不能被修改。

例二:指针变量的值可以被修改

char *p = "hello"; //字符指针指向字符串常量
char ch = 'a';
p = &ch; //指针变量指向可以改变
说明:定义一个字符指针指向字符串常量“hello”,同时定义一个字符变量ch,改变指针变量的指向,即让p指向字符变量ch,这样是可以的,即指针变量的指向是可以改变的。
(2)字符串数组内容可以被修改,但字符串数组名所代表的字符串首地址不能被修改

发布了23 篇原创文章 · 获赞 34 · 访问量 3万+

猜你喜欢

转载自blog.csdn.net/alangaixiaoxiao/article/details/103024092
今日推荐