如何正确使用指针(指针作为输出型参数)与结构体指针作为函数参数
2017-02-10 15:12
513 查看
如何正确使用指针(指针作为输出型参数)与结构体指针作为函数参数
通俗的讲,指针作为某一函数的实参,在函数内部发生改变后,外部的值也能跟着发生变化以下内容是小项目开发随笔:(与标题相关内容在错误3)
错误1:
built-in.o: In function `main': /root/winshare/ImagePlayer/main.c:17: undefined reference to `fb_open'
但是明明有定义啊?不是这个原因,而是文件没添加到工程中来
Makefile:
#添加顶层目录下的子文件夹(注意目录名后面加一个/) obj-y += display/
然后子文件夹下添加相应规则
(子)Makefile
obj-y += framebuffer.o
错误2:
…
错误3:
编译通过,但执行发生段错误,指针出错。通过这一错误进一步加深了对指针的使用类比外部的int a作为函数形参并能够传出来,要用指针形式
外部的指针作为函数形参并能够传出来,要使用指针的指针作为形参类型
如下案例:
程序1:
void myMalloc(char *s) //在函数中分配内存,再返回 { s=(char *) malloc(100); } void main() { char *p=NULL; myMalloc(p); //这里的p实际还是NULL,p的值没有改变 if(p) free(p); }
程序2:
void myMalloc(char **s) //指针的指针,双重指针类型 { *s=(char *) malloc(100); } void main() { char *p=NULL; myMalloc(&p); //这里的p可以得到正确的值 if(p) free(p); }
附.重要:
实际开发中,更喜欢利用结构体指针。因为如果不使用结构体指针,那么函数里面将会有一堆的解引用结构体指针作为函数参数
void fb_open(struct framebuffer *fb)//指针 { ... } 4000 void main() { struct framebuffer fb0; fb_open(&fb0);//取地址符& struct framebuffer* fb1;//需要给这个指针分配实体 fb1 = (struct framebuffer*)malloc(); fb_open(fb1);//这时就不用取地址符,fb1中的成员的值在fb_open中被改变会影响 }
详细例子说明
#include <stdio.h> #include <stdlib.h> struct test_t{ int *p; int a; int b; int c; int d; }; //函数外部使用malloc测试函数 (函数形参为结构体类型) void func1(struct test_t * test) { test->a += 1; printf("test->a = %d.\n", test->a); } /* 以下为函数内部使用malloc测试函数 (函数形参为结构体类型) */ void func2(struct test_t * test) { test = (struct test_t *)malloc(sizeof(struct test_t)); test->b = 1; printf("test->b = %d.\n", test->b); } //...func3... void func4(struct test_t **test) { *test = (struct test_t *)malloc(sizeof(struct test_t)); (*test)->d = 1; printf("test->d = %d.\n", (*test)->d); } void func_p(struct test_t * test) { test->p = (int *)malloc(sizeof(struct test_t)); } int main(void) { //使用案例1:函数外malloc struct test_t * t1; t1 = (struct test_t *)malloc(sizeof(struct test_t)); t1->a = 1; func1(t1);//这样使用,t1->a的值就会改变,和func4(struct test_t **test)区分 printf("test->a = %d.\n", t1->a); free(t1); //有时候需要在函数里面malloc,如下: #if 0 //使用案例2:错误使用,编译通过,运行触发段错误 struct test_t * t2; func2(t2); printf("test->b = %d.\n", t2->b); free(t2); #endif #if 1 //但是可以在结构体里声明一个指针成员,然后如下使用 //(实际上原理和案例1是一样的,外部需要有实体,但是这里还提出来,是因为想说一下free的问题) //为结构体内部的指针分配内存还是经常遇到的,包含该指针的结构体也是malloc而来的,但是有时只记得free最外层的指针 struct test_t * t0; t0 = (struct test_t *)malloc(sizeof(struct test_t)); func_p(t0); printf("test->p = %p.\n", t0->p); free(t0->p);//不会触发段错误,注意free这个指针,还要注意先free这个指针,再free t0 free(t0); #endif #if 0 //使用案例3: struct test_t * t3; t3 = 返回值为struct test_t *的func3函数; ... #endif //使用案例4:(func4形参使用双重指针类型) struct test_t * t4; func4(&t4); printf("test->d = %d.\n", t1->d); free(t4); //个人常用的就上面几种,当然还有这里没列出来的使用方式 /** 总结 * >> 函数使用指针类型形参以提高效率 * (1)外部定义指针变量再malloc分配 * (2)函数外部的指针在函数内部malloc后能得到分配的内存地址的两种方式:双重指针和返回值 * 多多编程多多体会 */ return 0; } 打印内容: test->a = 2. test->a = 2. test->p = 0x81ed020. test->d = 1. test->d = 1.
另外:在C语言中,使用结构体的时候 “->” 和 “.” 有什么区别?
定义的结构体如果是指针,访问成员时就用-> 如果定义的是结构体变量,访问成员时就用. 例如: struct AAA { int a; char b; }; struct AAA q; 访问成员就用:q.a; struct AAA *p; 访问成员就用:p->a;
相关文章推荐
- 正确使用指针(指针作为输出型参数)与结构体指针作为函数参数
- 《IOS_作业C语言》高级指针(结构体指针、结构体数组指针、结构体数组指针,作为函数的参数使用、预编译指令)
- 指针(指针作为输出型参数)与结构体指针作为函数参数(树),以及函数内存
- 《IOS_C语言》高级指针(结构体指针、结构体数组指针、结构体数组指针,作为函数的参数使用、预编译指令)
- C语言--- 高级指针2(结构体指针,数组作为函数参数)
- [编程] C语言结构体指针作为函数参数
- 结构体变量、结构指针变量、结构数组作为函数的参数应用实例分析
- 如何理解数组作为函数参数时,数组名就是指针?
- C语言-----内存与指针(3) How 4000 do you pass a string to a function如何给一个函数传入字符串作为参数:
- c语言_函数指针作为函数参数的使用
- 实例解析使用指针作为函数参数传递需要注意的问题
- 漫谈C指针:函数指针作为函数参数使用
- 结构体变量、结构指针变量、结构数组作为函数的参数应用实例分析
- 如何正确为函数参数中的指针动态分配内存
- 使用指针作为函数返回值和参数的问题总结
- 83 js 如何正确传递DOM元素的指针 选择器内参数为变量 论js函数的简化 seajs用法
- 结构体变量、结构指针变量、结构数组作为函数的参数应用实例分析
- 结构体变量、结构指针变量、结构数组作为函数的参数应用实例分析
- 结构体指针作为函数参数
- 指针数组作为函数参数的使用问题