关于结构体变量在多文件工程中的问题

使用ICCAVR开发AVR单片机的过程中遇到这样的问题:

问题描述:

一个结构体变量在文件file1.h中声明如下:

  
  
  
  
  1. #ifndef __FILE1_H 
  2. #define __FILE1_H 
  3.  
  4. struct PID  
  5. int Reference; 
  6. int FeedBack; 
  7.  
  8. int Ka; 
  9. int Kb; 
  10. int Kc; 
  11.  
  12. int ControlValue; 
  13.  
  14. } speedPID; 
  15. void PIDInit ( struct PID *p ); // PID参数初始化 
  16.  
  17. #endif 

其对应的.c文件:file1.c中如下:

  
  
  
  
  1. #include "file1.h" 
  2.  
  3. void PIDInit ( struct PID *p ) 
  4. .... 

在file2.c中,加入了#include"file2.h"一句包含,并且相应函数中用到了这个结构体变量,对它的成员变量进行了赋值。也就说该结构体是一个全局变量。
file2.h中内容:

  
  
  
  
  1. #ifndef __FILE2_H 
  2. #define __FILE2_H 
  3.  
  4. extern struct PID speedPID;         
  5. extern void PIDInit( struct PID *speedPID ); 
  6.    
  7. #endif 

但是用ICCAVR编译时,提示

 

  
  
  
  
  1. file2.c(102): unknown field `Reference' of `incomplete struct PID defined at C:\DOCUME~1\baifeng\file2.h'  
  2.  
  3. C:\iccv7avr\bin\imakew.exe: Error code 1 
  4. Done: there are error(s). Exit code: 1 

解决方法:

file1.h->

 

  
  
  
  
  1. #ifndef __FILE1_H 
  2. #define __FILE1_H 
  3.  
  4. extern struct PID  speedPID; 
  5. void PIDInit ( struct PID *p ); // PID参数初始化 
  6. void PID_reload ( struct PID *p, int ref, int a, int b, int c ); 
  7.  
  8.  
  9. #endif 

file1.c->

 

 

  
  
  
  
  1. #include "file1.h" 
  2.  
  3.  
  4. struct PID  
  5.  int Reference;   
  6.  int FeedBack;    
  7.   
  8.  int Ka;   
  9.  int Kb;   
  10.  
  11.  int Kc;   
  12.    
  13.  int ControlValue;   
  14.    
  15. } speedPID;   
  16.  
  17.    
  18. void PIDInit ( struct PID *p ) 
  19. {  
  20.     ...... 
  21.   
  22. // 更新PID参数 
  23. void PID_reload ( struct PID *p, int ref, int a, int b, int c ) 
  24.     p->Reference = ref; 
  25.     p->Ka = a; 
  26.     p->Kb = b; 
  27.     p->Kc = c; 

file2.c等文件中,加入#include "file1.h",然后直接使用PIDInit()和PID_reload()函数就可以了。

 

 

评论:

    的确是在头文件中定义全局变量不太好,特别是结构体这种变量,虽然加入了#ifndef这样的宏,但是在编译时编译器还是会报重复定义之类的错误。 
    另外,还查看了ICC的自带头文件,也都是没有声明变量的,仅仅声明了库函数和相关的宏定义。

    所以,相关的全局变量放在.c中定义;如果需要在别的文件中修改变量,特别是结构体变量的分量,还是专门编写一个函数的好,结构体的形参使用地址传递。

    从这点上,也可以体会出面向对象编程的好处,不会在类的外部随便修改成员变量,而是通过相应的方法(成员函数)达到相同的目的。同时,形参还比面向过程编程少一个。

 

 

你可能感兴趣的:(多文件,结构体,工程,avr,Icc)