马上注册,结交更多好友,享用更多功能^_^
您需要 登录 才可以下载或查看,没有账号?立即注册
x
cpp源文件与h头文件关系 我们知道C++支持多种编程范式,可以完全用采用面向过程,不去用类,当然了很少有人这样做,一般是结合面向过程与面向对象. 那假如有一些处在不同源文件中的变量和函数(不是类中的变量成员或成员函数),我们要使用不同源文件中的变量或函数时咋整呢? 在面向对象中我们使用一个个类的时候自然是用头文件引用下就OK.但现在没有类,只是一个个变量和函数,也能用引用头文件吗 ? 这得看情况,有时可以,有时不行.如果头文件中只有外部声明没有任何定义,那引用头文件完全没有问题.如果头文件中有定义的话,如果只被一个cpp文件引用则没问题,如果被多个cpp文件引用就会出现重复定义的错误.(注:编译器是以cpp文件为单位编译,如果某个h头文件没有被引用的话相当于被抛弃不用了.引用头文件时预编译时只是简单的把头文件复制到引用它的cpp文件中.) extern外部声明 假如在有one.cpp和two.cpp两个源文件. //one.cpp中 --------------------------------------------------- #include using namespace std; int number = 123; //number的定义 void Print() {cout<<"hi,i am one.cpp"<<endl;}</endl;} //two.cpp中 -------------------------------------------------------- #include using namespace std; extern int number;//这就是所谓的外部声明,此处extern不可省 extern void Print(); //此处extern可以省略. cout<<number; p="" 结果为123 Print(); //输出i am one.cpp 在two.cpp中是怎么得到one.cpp中的number的值的呢,由于用extern int number这样声明了下,表明number在其他源文件中有定义,链接器就会帮助去其他源文件中找的. 假如把上面two.cpp中的extern关键字去掉. 编译时不会出错.但链接时出错了,重复定义了.因为one.cpp中已经定义了个number,不能再定义一个相同的了. static 内部连接 上面的例子中我们知道one.cpp和two.cpp中同时写上int number会出错,说重复定义了.但如果这样 //one.cpp中 static int number = 123; //two.cpp中 static int number; //没显式赋值,会默认赋予0 此时却不会出错.因为定义变量时默认是外部连接的.而加上关键字static表示是静态变量,是内部连接,链接器不会去看不同cpp编译成的obj文件中有重名的静态变量不. 当用static修饰后就不能再使用extern修饰了. //one.cpp中 static int number = 123; //two.cpp中 extern int number; cout<<number;</number; 此时会出错,因为extern声明的number找不到定义.因为one.cpp的number用static修饰表明是内连接了. const关键字 //one.cpp中 const int number = 123; //two.cpp中 const int number = 321; 这里达到的效果与static一样,都属于内部连接,所以不会出错.唯一不同的时const表示常量,定义时必须显式赋予值,且赋值后不能再改变它的值. [NextPage]
不过const还有另外一个特性就是可以和extern一起用. 比如在two.cpp中这样写 extern const int number; // cout<<number; p="" 输出的值是one.cpp中的number值123 inline与static函数也是内部连接的 //one.cpp中 void Test() { } //two.cpp中 void Test() { } 这样编译时会报错,重复定义了.但如果把上面的两个void Test都改成inline void Test() { }或者static void Test() { }则不会出错.//注意这里讲的inline函数指的是全局函数,不是类里面的inline函数. 所以函数跟一般变量差不多.没任何修饰的就默认是外部连接,有static修饰的则是内部连接.另外没有const函数这一说,只有在类中才可以在函数后面加个const来修饰
|