新闻  |   论坛  |   博客  |   在线研讨会
C语言中的传值调用和引用调用
gsfei2009 | 2009-05-28 01:05:28    阅读:1494   发布文章

        在使用一个音频芯片时,需要用到这样一个功能,即对音量进行调节。在厂家提供的驱动里面没有这样的功能函数,因此需要自行添加。注意到厂家提供的驱动里面包含了一个写入命令的函数,void Vol_Cmd(uint 8 vol), 其中vol是音量的数值,范围为0~255,这个函数的作用就是通过写入vol的值来改变音量。

  因此实现音量调节的思路就有了:

  把当前vol的值相应的增加或者减少,然后再调用Vol_Cmd()函数把它写入到芯片中,就实现了音量的增减。很简单吧。但是有一个问题,那就是要注意到Vol_Cmd()函数是没有返回值的,那么vol的值怎么样才能更新呢?也就是说,怎样才能获得vol的当前值呢?

  我最开始的想法是构造这样两个函数(以音量增加为例,音量减少类似):

  uint8 Vol_Inc(uint8 vol)

  { if(vol<=0xf0)

   vol+=0x0f;          //以15作为增量,从音量最小到最大一共有16档

   Vol_Cmd(vol);

   return vol;

  }

  很明显,我的想法是在 Vol_Inc()函数中做两件事,一件事是把vol的值增加之后写入到芯片中,实现音量的增加,另一件事是把增加后的值返回,以便下次调用Vol_Inc()函数的时候vol的值已经更新。那么调用这个函数就必须遵循这样的格式:

   uint8 vol="120";          // 初始化为一个中间值

   vol=Vol_Inc(vol);    

  当然这样是没有错误的,不过在板子上调试的时候却发现一个问题,那就是调用Vol_Inc()函数的次数不能连续超过六次,否则音量就变为0。Debug的时候单步跑到Vol_Inc()函数的时候就warning,然后error。研究了很长时间都没有解决这个问题。

  同project leader沟通之后,他表示音量调节只需要5档就够了,但是最好还是要保持程序的flexibility。只需要5档?我把增量的值改为0x32之后放到板子上跑,这下就一切正常了,音量加减都没有问题。

  问题看似解决了,但是我还是觉得不舒服。vol=Vol_Inc(vol);这个调用看来起很不舒服。抛开这个具体的问题,我想了一下函数调用的问题。想到指针的时候,我发现自己犯傻了。

  C语言的函数调用采用的是传值调用,也就是说调用函数之后并不改变传递的原始参数的值,传递给子函数的只是一个副本,下面举例说明:

  #include "stdio.h"

  #include "stdlib.h"

  void Vol_Inc(int p);

  main()

  { int vol="100";

     Vol_Inc(vol);

    printf("vol=%d\n",vol);

    system("pause");

  }

  void Vol_Inc(int p)

  { p+=15;

  }

  很明显,输出为vol=100;因为main在调用Vol_Inc()的时候只是把vol=100的一个副本传递给Vol_Inc(),调用之后vol的原本没有变,因此vol值并不会改变。但是这个音量加减程序要改变原本的值,怎么办? 很简单,用指针。与传值调用相对应的是引用调用(call by reference),C语言并不支持,只能通过使用指针参数来模仿。

  #include "stdio.h"

  #include "stdlib.h"

  void Vol_Inc(int *p);

  main()

  { int vol="100";

     Vol_Inc(&vol);

    printf("vol=%d\n",vol);

    system("pause");

  }

  void Vol_Inc(int *p)

  { *p+=15;

  }

  这下输出就是vol=115了,也就是说我的目的达到了。按照这个思路修改了一下音量增减的函数,放在板子上运行,完全正常。难道以前的vol=Vol_Inc(vol)调用有问题?我怀疑是。不管了,我也没有精力去深究了,反正这个问题已经解决了。

 

  经验教训:

  这个问题是一个初级得不能再初级的C语言问题,自己怎么就在开始走了弯路呢。埋头做项目的时候,思路太窄,不能把以往学习的知识很好的应用起来。前天一个师兄在QQ群里也说道,大家都在做项目,几乎都没有怎么静下心看书,其实书上很多的地方都写得很清楚了……

*博客内容为网友个人发布,仅代表博主个人观点,如有侵权请联系工作人员删除。

参与讨论
登录后参与讨论
推荐文章
最近访客