40篇学完C语言——(第七篇)地址算术运算

Posted xcc_21

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了40篇学完C语言——(第七篇)地址算术运算相关的知识,希望对你有一定的参考价值。

当C语言中的指针执行数组元素时,C语言允许对指针进行算术运算。

指针运算

C语言支持3种格式的指针算术运算,包括指针加上整数,指针减去整数和两个指针相减。同时还可以用关系运算符进行指针比较。

  • 指针p加上整数j表示指针向后移动j个单位(每个单位大小为指针p的类型所占的字节数),指向p原先指向的元素后的第j个元素。若p指向数组a[i],则p+j指向a[i+j]
  • 指针p减去整数j表示指针向前移动j个单位,指向p原先指向的元素前的第j个元素。若p指向数组a[i],则p-j指向a[i-j]
  • 两个指针相减,得到的是指针之间元素的个数。若指针p指向a[i],指针q指向a[j],则p-q等于i-j
  • 指针的比较依赖于指针所指向的两个元素的相对位置。若指针p指向a[i],指针q指向a[j],pq的比较结果由ij的大小决定。

因此适用于指针运算的运算符包括算术运算符+-,赋值运算符和复合赋值运算符(=+=,’-=’,++--)和所有的关系运算符。

/**************************************
 * pointer_5.c                        *
 *                                    *
 * C语言中的指针运算                  *
 **************************************/

#include <stdio.h>
#define N 10

int main()

  int a[N], sum, *p;
  int i = 0;
  printf("请输入%d个整数:", N);
  for (;i < N; i++)
  
    scanf("%d", a + i);
  

  p = a;
  sum = 0;
  for (i = 0; i < N; i++)
  
    sum += *p;
    p++;
  

  printf("这%d个数的和为%d\\n", N, sum);

  return 0;

C语言的间接寻址运算符*常和++--运算符一起使用,具有以下四种不同的形式:

表达式 含义
p++或(p++) 首先计算表达式的值为*p,然后p自增1
(*p)++ 首先计算表达式的值为p,然后p自增1
++p或(++p) 首先将p自增1,然后计算表达式的值为*p
++p或++(p) 首先将(p)自增1,然后计算表达式的值为(p)
/**************************************
 * pointer_6.c                        *
 *                                    *
 * C语言中的自增自减和间接寻址运算符  *
 **************************************/

#include <stdio.h>

#define N 10

int main()

  int a[10] = 0,1,2,3,4,5,6,7,8,9;
  int temp = 0;

  int *p = a;
  printf("p的初始值为%p, *p值为%d\\n", p, *p);
  temp = *p++;
  printf("*p++的值为%d, 运算后p的值为%p, *p的值为%d\\n\\n", temp, p, *p);

  printf("p的初始值为%p, *p值为%d\\n", p, *p);
  temp = *(p++);
  printf("*(p++)的值为%d, 运算后p的值为%p, *p的值为%d\\n\\n", temp, p, *p);

  printf("p的初始值为%p, *p值为%d\\n", p, *p);
  temp = (*p)++;
  printf("(*p)++的值为%d, 运算后p的值为%p, *p的值为%d\\n\\n", temp, p, *p);

  printf("p的初始值为%p, *p值为%d\\n", p, *p);
  temp = *++p;
  printf("*++p的值为%d, 运算后p的值为%p, *p的值为%d\\n\\n", temp, p, *p);

  printf("p的初始值为%p, *p值为%d\\n", p, *p);
  temp = *(++p);
  printf("*(++p)的值为%d, 运算后p的值为%p, *p的值为%d\\n\\n", temp, p, *p);

  printf("p的初始值为%p, *p值为%d\\n", p, *p);
  temp = ++*p;
  printf("++*p的值为%d, 运算后p的值为%p, *p的值为%d\\n\\n", temp, p, *p);

  printf("p的初始值为%p, *p值为%d\\n", p, *p);
  temp = ++(*p);
  printf("++(*p)的值为%d, 运算后p的值为%p, *p的值为%d\\n\\n", temp, p, *p);

  return 0;

指针和数组

可以用数组的名字作为指向数组第一个元素的指针。但数组名是指针常量,不能赋值。

函数中数组形式的形式参数传入的都是指针,为了明确指针形式,可以将数组型形式参数该为指针,两者是完全一样的。

同样,指针也可以作为数组名一样使用,指针p的表达式p[i]等价于*(p+i)

多维数组的元素在内存中是依序存储的,获得第一个元素的指针,就可以通过重复自增指针的方式访问到每一个元素。

C语言中n维数组是被当成一个一维数组,每个数组元素是一个n-1维数组,依次类推。因此对于数组int a[N1][N2]...[Nm]来说,a是一个一维数组的指针,其元素是一个n维数组,因此a指针增减的移动单位是n维数组,a[N1]是一个一维数组的指针,其元素是一个n-1维数组,因此a[N1]指针增减的移动单位是n-1维数组,依次类推,a[N1][N2]...[Nm-1]是一个一维数组的指针,其指针增加的移动单位是一个int型长度,指针指向的是int型的数组元素。

/**************************************
 * pointer7.c                         *
 *                                    *
 * C语言中指针和数组                  *
 **************************************/

#include <stdio.h>

#define N 10

void ReversePrint(int a[])

  int *p = a + N - 1;
  for (; p >= a; p--)
    printf("%d ", *p);


int Sum(int *a)

  int *p = a;
  int sum = 0;
  for(; p < a + N; p++)
    sum += *p;
  return sum;


int main()

  int a[N];
  printf("请输入%d个整数", N);
  int i = 0;
  for (; i < N; i++)
    scanf("%d", &a[i]);

  printf("10个数的反序排列为:");
  ReversePrint(a);
  printf("\\n");
  printf("这%d个整数的和为%d\\n", N, Sum(a));

  return 0;

参考文献

  1. K.N. King 著,吕秀峰 译. C语言程序设计-现代方法. 人民邮电出版社
  2. https://www.coursera.org/course/pkuic

以上是关于40篇学完C语言——(第七篇)地址算术运算的主要内容,如果未能解决你的问题,请参考以下文章

Linux篇第七篇——进程地址空间(程序地址空间+虚拟地址空间)

一篇学完 Tomcat

第七篇 -- 2020期待

C++初阶第七篇——C/C++的内存管理(C/C++动态内存分布+new和delete的用法和实现原理)

C语言基础:指针相关概念(指针的算术运算 指针数组指向指针的指针 传递指针给函数 从函数返回指针 )为啥C 语言不支持在调用函数时返回局部变量的地址?

第七篇 爬虫挖矿神器看这篇就够了