您还未登录! 登录 | 注册 | 帮助  

您的位置: 首页 > 软件开发专栏 > 开发技术 > 正文

数组和指针的关系

发表于:2017-08-08 作者:幻世 来源:

  数组名是个常量指针(const pointer)?
  你TM在逗我?数组名只是个名字,你能给它个类型?
  像下面这些命题:
  数组是指针
  数组是指针常量
  数组是常量指针
  数组名是常量指针
  数组名是指针常量
  统统,统统都是错的。后两个是扯淡,变量名字也有类型??这些其实都是说的是数组,不管行为怎样令人迷惑,但都是说的数组,不应该有数组名是xxx这个说法。
  说下性质:
  int a[10] = { 0 };
  int * ptr = NULL;
  int * const cptr = NULL;    // const pointer
  int const * ptrc = NULL;    // pointer to const
  (这里不使用指针常量和常量指针这两个概念,这两个概念细究并不严谨,这里使用const pointer 和 pointer to const)
  数组的性质:
  数组是复合类型,a 的类型是 type[size]
  大小为sizeof(a) = sizeof(int[10])
  在C/C++中数组a的值取首地址的值,这个值由编译器保存
  对数组取址&a,&a和对其他的对象&的行为是相同的,并且&a指向的是一个int[10]的类型的量,这就是为什么(&a + 1)的值相对于a的首地址增加了sizeof(int [10])。
  数组a的值(不是元素值)为什么不可以改变,这是因为数组这个类型就没有这个运算呀!这是由它的实现决定的。
  const pointer
  这个就是个不可更改值的指针,没有什么特别的,指针也是复合类型,它的类型是int * const。
  还有令人迷惑的是,数组和指针的一些用法或者说是行为非常的相近,这些地方可以说是把数组隐式的转换为了指针。
  比如作为函数参数时,这几种形式是等价的:
  void f1(int a*);
  void f2(int a[]);
  void f3(int a[10]);
  并且虽然2和3在形式上是数组,但实际上是指针变量,为什么呢,很显然下面的例子可以说明这个:
  // 当我传入一个数组时,不会有问题,无论形参是怎样的,都是一个指针
  void f3(int a[10])
  {
  a += 10;
  }
  还有对数组和指针的下列操作:
  int b = *(a + 1);
  int c = *(ptr + 1);
  *(a + 1)和*(ptr + 1)的实现应该是一样的(看编译器了),在这些地方,数组有和指针一样的行为。
  最后,对C语言的一些用法扣得太深感觉意义不大,很多算是当初设计者考虑不周的地方。C的抽象层次比较低,像数组和结构体基本可以用内存+地址描述出来,而且学过编译原理的应该对他们的实现有一定的了解,本质很简单的东西,设计的不好,抽象后行为也可能令人很迷惑。