指针数组与数组指针 和 函数指针与函数指针数组

很容易混淆的概念其实并不难理解

1,指针数组;

看字面意思就知道这一定是一个数组,里面的原酸全部是指针

例如,定义一个简单的指针数组

char  *p[10];   //这就是一个包含十个字符指针的数组。

例:

#include<stdio.h>
int main()
{
 char *p[7];
 char arr[] = "abcdef";
 int i = 0;
 for (i = 0; i < 7; i++)
 {
  p[i] = arr;
 }
 printf("%s", p[6]);
}

输出结果是abcdef.

这个简单的程序就用到了指针数组,他定义了一个数组包含了7个字符指针,for循环每一个指针都指向了arr数组定义的字符串。

2,数组指针

从名字上看就能知道他是一个指针,是一个指向数组的指针。

例如:

#include<stdio.h>
int main()
{
 char arr[6] = "abcde";
 char(*p)[6] = &arr; //数组指针才能取数组的地址。
 printf("%s", *p);
}

这个简单的程序最后的输出结果当然是arr字符数组中的内容了。

通过数组指针也能更改数组中的内容,对于上面的程序*((*p)+1)=‘a‘;就把第二个元素改成了‘a’;*p便是arr的地址。

3,函数指针

一样,从名字上看,这便是一个指向函数的指针,他是如何定义的呢,

例:

int num(int a,int b)

{

return a+b;

}

int mian()

{

int (*p)(int ,int )=num; //这便是一个指向num函数的一个函数指针了,int 是函数的返回值,

后面是数据类型,它所指向的函数必须和他有同样的返回值和数据类型。

int ret=(*p)(10,20);

printf("%d",ret);//结果是30.

}

4,函数指针数组

从名字上也能看楚这首先是一个数组,数组元素是指针,而每一个指针都指向了一个函数,这个麻烦的东西有什么用了,

事实证明他在某些地方非常有用处,首先来看他是如何定义的

例:

int (*p[4])(int ,int)

//这便是一个有4个元素的函数指针数组了,这个数组中的每一个指针指向的函数必须是一样的数据类型和返回值。

具体有什么用我们来看一段代码。

这个代码是一个简单的计算器。

#include <stdio.h>
void print_menu()
{
 printf("**********************\n");
 printf("*** 1.add   2.sub  ***\n");
 printf("*** 3.mul   4.div  ***\n");
 printf("******* 0 exit  ******\n");
 printf("**********************\n");
}
int add(int x, int y)     
{
 return x + y;
}
int sub(int x, int y)
{
 return x - y;
}
int mul(int x, int y)
{
 return x * y;
}
int div(int x, int y)
{
 if (y == 0)
 {
  printf("除数为0\n");
  return -1;
 }
 return x / y;
}
int(*pfun[5])(int, int) = {0,add, sub, mul, div};
//函数指针的数组(转移表)
int main()
{
 int input = 1;
 while (input)
 {
  int n1 = 0;
  int n2 = 0;
  int ret = 0;
  print_menu();
  printf("请选择>:");
  scanf("%d", &input);
  printf("请输入两个操作数>:");
  scanf("%d%d", &n1, &n2);
  ret = pfun[input](n1, n2);
  /*switch (input)          //如果不用函数指针数组便要用switch来实现,可以看出如果计算器功能很多,那么
                              代码也会相当庞大
  {
  case 1:
   ret =add(n1,n2);
   break;
  case 2:
   ret = sub(n1, n2);
   break;
  case 3:
  ret = mul(n1, n2);
   break;
  case 4:
   ret = div(n1, n2);
   break;
  }*/
  printf("ret = %d\n",ret);
 }
 return 0;
}

可以看出此时函数指针数组大大减少了代码的长度。

时间: 2024-10-15 03:57:03

指针数组与数组指针 和 函数指针与函数指针数组的相关文章

qsort 函数的使用——对普通数组、指针数组、二维数组中的元素进行排序

在ANSI C中,qsort函数的原型是 #include <stdlib.h> void qsort(void *base, size_t nmemb, size_t size, int (*compar) (const void *, const void *)); 解释:qsort函数对含有nmemb个元素的数组进行排序,而base指针指向数组的第一个元素.这个数组的元素个数由size指定. compar函数对qsort的比较操作进行定义,所以可以定制数字的比较,字符串的比较,甚至结构体

剑指offer_面试题14_调整数组顺序使奇数位于偶数前面(函数指针用法)

题目:输入一个整数数组,实现一个函数来调整该数组中数字的顺序,使得所有奇数位于数组的前半部分,所有偶数位于数组的后半部分. 1.一般想法,不考虑时间复杂度: 每次遍历数组,碰到一个偶数就拿出来,将后面所有数字向前挪动一位,在将该偶数放到最后. 2.利用冒泡排序的思想,两个指针,一前以后,如果前为偶数,后为奇数,就交换. 算法如下: void Reorder_array(int p[],int length) { if(NULL == p || length <= 0) return; int i

c/c++ 函数、常量、指针和数组的关系梳理

压力才有动力,15年中旬就要准备实习,学习复习学习复习学习复习学习复习……无限循环中,好记性不如烂笔头……从数组开始,为主干. c 的array由一系列的类型相同的元素构成,数组声明包括数组元素个数和类型,c 中的数组参数是引用形式传参(传址调用),而常量标量是按值传递. //[]方括号表示声明的是数组,里面的数字表明了数组包含的元素数目 int states[50];//声明50个整数的数组 double code[365];//声明365个浮点数的数组 char chr[20];//声明20

函数指针和指针函数和回调函数以及函数指针数组

1.首先来说,函数指针 就是函数的指针 2.指针函数,就是指针的函数.也就是返回值是个指针 一.指针 [1]指针  1--- 指针变量:用于存放地址量的变量  2--- 地址常量   int a = 20:   int *p = &a: [2]运算符  1--- &  2--- *(指针解引用):通过地址获取其内容  3--- []:只针对于指针运算.指针加单位长度,后取*运算. 二.函数 [1]指针函数 [2]函数指针 [3]函数指针数组  本质:数组,由多个元素组成  元素:函数指针类

黑马程序员---C基础12【结构体数组】【结构体指针】【结构体嵌套】【作为函数参数】【枚举类型】

------Java培训.Android培训.iOS培训..Net培训.期待与您交流! ------- [结构体数组] 1.结构体数组: 结构体数组的每一个元素都是具有相同结构类型的下标结构变量:(可以表示一个群体,一个班学生档案) 2.结构数组定义: 定义格式: struct    结构名{ 成员列表: }数组名[数组长度]: 1 1)定义结构体的同时定义数组: 2 3 struct stu{ 4 5 int num; 6 7 char name[10]; 8 9 int age; 10 11

指针数组,数组指针,函数指针,main函数实质,二重指针,函数指针作为参数,泛型函数

 1.指针数组 数组里面的每个元素都是指针. 指针数组的案例如下: 易犯错误: 2.数组指针 归根结底还是指针,只是取*的时候能够取出一整个数组出来. 数组指针:(一个指针指向了数组,一般和二维数组搭配使用). 下面的(p+1)表示的是加过20个字符. 3.函数指针: 在gcc编译的时候增加一些调试信息的方式是: gcc demo.c –g –o app   -g表示增加一些调试信息 objdump –dSsx app > file   将app反汇编,然后重定向到file文件中.函数指针定

c语言数组做函数参数退化为指针

我的系统是MAC OS 64位.根据自己的系统位数不同是有差异的.以下是我学习过程中遇到的问题 大侠略过... 有时候我们想通过一个函数对数组的元素进行操作,在sizelen函数中想想通过sizeof获得数组的长度. 想法是好的,不要以为你对C语言很了解了.其实数组在做函数参数是只是传了,一个指针.也就是数组 的首地址. 从结果可以看出,C编译器确实是这么做得.我的系统是64位,所以int *是占8个字节. 以上只是我学习过程中遇到的问题.大侠略过...

C语言 数组做函数参数退化为指针的技术推演

//数组做函数参数退化为指针的技术推演 #include<stdio.h> #include<stdlib.h> #include<string.h> //一维数组做函数参数退化为指针的技术推演 void printfA(char * strarr[3]); //计算机中,数组都是线性存储,二维数组元素也是一个个的排列的 //例如: 1,2,3,4,5,6,7,8,9 像这组数据 我们可以认为是一维数组 int a[9]={1,2,3,4,5,6,7,8,9}; //也

C/C++中数组作为函数形参后退化为指针

最近写了一个函数,把数组作为了它的参数,在这个函数中用到了这个数组的长度,按照正常的求长度的方式,应该不会出错:但是运行之后发现结果却不是我想要的.于是写了一个测试程序来验证我的猜想. #include <iostream> using namespace std; void Sort(int nSortArray[6]) { int nLen = sizeof(nSortArray) / sizeof(nSortArray[0]); int nTmp = 0; for (int i = 0;

c 数组做为形参时 该参数退化为指针

当数组做为函数的形参的时候,该参数退化为指针,并且是无法直接求得数组的大小. 传数组给一个函数,数组类型自动转换为指针类型,因而传的实际是地址. void func(int array[10]) void func(int array[]) void func(int *array) 所以以上三种函数声明完全等同. 实际情况是,数组做参数,完全无法按值传递.这是由C/C++函数的实现机制决定的. 通常计算数组大小的方式如下: int len = sizeof(arr)/sizeof(type)