当前位置 : 主页 > 编程语言 > c语言 >

指针的进阶

来源:互联网 收集:自由互联 发布时间:2023-09-06
03数组参数、指针参数 一维数组传参 #include stdio.h//形参写成数组形式void test(int arr[]){}void test(int arr[10]){}/形参写成指针形式void test(int *p){}void test2(int *arr[]){}void test2(int *arr[20]){}void test

03数组参数、指针参数

一维数组传参

#include <stdio.h>

//形参写成数组形式
void test(int arr[])
{}

void test(int arr[10])
{}

/形参写成指针形式
void test(int *p)
{}

void test2(int *arr[])
{}

void test2(int *arr[20])
{}

void test2(int** p)
{}

int main()
{
  int arr[10] = {0};
  int *arr2[20] = {0};
  test(arr);
  test2(arr2);
  
  return 0;
}

二维数组传参

//形参写成数组的形式
void test(int arr[3][5])
{}
//1. 行可以省略,但列不能省略
void test(int arr[][5])
{}

//形参写成指针形式
//1. 列不可省略
//2. *p指向的是第一行的地址,5代表一行有多少个元素
//3. int *p[5]是错误的,它是一个指针数组
void test(int(*p)[5])
{}

//错误写法
//1. 一级指针接受普通变量的地址
void test(int *arr)
{}

//2. 第一行的地址放在了一个数组里,错误
void test(int* arr[5])
{}
//3. 二级指针是用来存放一级指针地址
void test(int** arr)
{}


int main()
{
  int arr[3][5] = {0};
  test(arr)
    
    return 0;
}

一级指针传参

案例:一级指针传参遍历数组并打印;

void test(int* ptr, int sz)
{
	int i = 0;
  for(i = 0; i < sz; i++)
  {
    printf("%d ", *ptr);
    ptr++;
  }
}

int main()
{
  int arr[10] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
  int* p = arr;
  int sz = sizeof(arr)/sizeof(arr[0]);
  test(p, sz);	//p是一级指针
  
  retuen 0;
}

当形参是一级指针的时候 int* ptr,实参有以下情况:

//一级指针
int a = 10;
test(&a);

int *p = &a;
test(p);

//数组
int arr[10];
test(arr)

二级指针传参

void test(char** ppc)
{}

int main()
{
	char a = 'w';
  char* pa = &a;
  char** ppa = &pa;
  
  test(ppa);
  
  return 0;
}

当函数的参数为二级指针的时候test(char** ppc),实参有如下情况:

char ch = 'a';
char* pc = &ch;
char** ppc = &pc;

char* arr[4];

test(arr);
test(&pc);
test(ppc);

函数指针

指向函数的指针,

int Add(int x, int y)
{
  return x + y;
}

int test(char* str)
{}

int main()
{
	int arr[10];
  int (*p)[10] = &arr;	//p是一个数组指针变量
  
  //函数地址
  printf("%p\n", &Add);
  printf("%p\n", Add);
  int (*pf)(int int) = Add;	//pf就是函数指针变量
  int (*pt)(char*) = test;

  //调用函数
  int ret = (*pf)(2,3);
  //int ret = pf(2,3);
  //int ret = Add(2,3);
  printf("%d\n", ret);

  return 0;
}

来自《C陷阱与缺陷》的一个例子:如何解释

  1. (*(void(*)())0)()
  2. void(* signal(int, void(*)(int)))(int)
int main()
{
  //代码1:
  //void(*)() 是一个函数指针类型
  //(void(*)()())0 对0进行强制类型转换
  //(*(void(*)()())0)()
  //1. 首先是把0强制类型转换为一个函数指针类型,这就意味着0地址处放一个返回类型是void,无参的一个函数
  //2. 调用0地址处的这个函数
  
  //代码2:
  //函数声明:int Add(int, int)
  //signal是一个函数声明
  //signal函数的参数,第一个是int类型,第二个是void(*)(int)的函数指针类型
  //signal函数的返回值类型也是:void(*)(int)的函数指针
  //简化:
  //typedof void(* pf_t)(int);	//给函数指针类型void(*)(int)重新起名叫:pf_t
  //pf_t signal(int,pf_t);
  
  return 0;
}

函数指针数组

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)
{
	return x/y;
}

int main()
{
  //指针数组
  //字符指针数组
  char* arr[5];
  
  //整形指针数组
  int* arr2[4];
  
  int (*pf1)(int, int) = Add;
  int (*pf2)(int, int) = Sub;  
  int (*pf3)(int, int) = Mul;
  int (*pf4)(int, int) = Div;
  
  //函数指针数组
  int (*pf[4](int, int)) = {Add, Sub, Mul, Div};
  int i = 0;
  for(i = 0; i<4; i++)
  {
		pf[i](8,2);
    printf("%d\n", ret);
  }
  return 0;
}

案例:设计一个简单的计算器

#include <stdio.h>
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)
{
  return x / y;
}

void menu()
{
	printf("**************************\n");
	printf("****  1.add   2.sub   ****\n");
	printf("****  3.mul   4.div   ****\n");
	printf("****  0.exit          ****\n");
	printf("**************************\n");
}
int main()
{
	int input = 0;
  int x = 0;
  int y = 0;
  int ret = 0;
  
  //转移表
  int (*pfArr[])(int, int) = {0, Add, Sub, Mul, Div};
  
  do
  {
    menu();
    printf("请选择:>");
    scanf("%d", &input);
    if(input == 0)
    {
      printf("退出计算器\n");
    }
    else if(input >= 1 && input <=4)
    {
      printf("请输入两个操作数:>");
      scanf("%d %d", &x, &y);
      ret = pfArr[input](x, y);
      printf("ret = %d\n", ret);
    }
    else
    {
      printf("选择错误\n");
    }
  }while(input);
  
  return 0;
}

03-10



上一篇:2011年湖南省对口高考真题
下一篇:没有了
网友评论