zoukankan      html  css  js  c++  java
  • 关于C++头文件的包含顺序问题

    个人菜鸟,发表下对头文件包含顺序的看法:

    首先是常规的包含:

    1 #include "a.h"
    2
    3  int
    4 main()
    5 {
    6 function_a();
    7 }

    这是一个在平常不过的包含了,主文件main.cpp包含头文件"a.h",当调用function_a()函数时,由于main.cpp

    文件中未包含function_a此函数的声明,那么它会到"a.h"这个文件中去找它的声明。如果在"a.h"这个文件中找不到,

    那么它回到"a.h"所包含的头文件中去找,这样一级一级往上找,直到找到或者找不到而报错为止。

    图中是最为平常的头文件包含。

    但是当我在看STL的源代码时却发现了问题,比如stl_vector.h这个文件中的一段代码:

    代码
    1 template <class _Tp, class _Alloc>
    2  void vector<_Tp, _Alloc>::_M_fill_insert(iterator __position, size_type __n,
    3 const _Tp& __x)
    4 {
    5 if (__n != 0) {
    6 if (size_type(_M_end_of_storage - _M_finish) >= __n) {
    7      ......
    8 fill(__position, __position + __n, __x_copy);
    9 }
    10 else {
    11 ......
    15 fill(__position, __old_finish, __x_copy);
    16 }
    17 }

    代码中有一个fill函数,但是stl_vector.h这个文件中却没有包含这个函数的实现,当我查找其所包含头文件时,却

    发现也没有包含这个函数的其它头文件,这时怎么回事呢,当我们想使用该头文件是编译器岂不是回报错?

    确实,如果我们直接包含该头文件,编译起将会报fill函数未定义的错误,那么到底是怎么回事呢?

    当我们查看vector这个文件时,真相大白:

    显然stl_vector.h文件被包含在vector之中,注意在stl_algobase.h文件中包含了fill的实现:

    stl_algobase.h
    template <class _ForwardIter, class _Tp>
    void fill(_ForwardIter __first, _ForwardIter __last, const _Tp& __value) {
    __STL_REQUIRES(_ForwardIter, _Mutable_ForwardIterator);
    for ( ; __first != __last; ++__first)
    *__first = __value;
    }

    fill这个函数在stl_algobase.h这个文件中。所以当我们在程序中写诸如:

    #include<vector>

    int
    main()
    {
      std::vector<int> vec;
    }

    这种代码时才不会报fill未找到的错误。但如果我们把vector文件中的包含顺寻更改如下:

    1 #ifndef __SGI_STL_VECTOR
    2  #define __SGI_STL_VECTOR
    3 ......
    4 #include <stl_vector.h>
    5 #include <stl_algobase.h>
    6  

    时,那就错了,为什么,因为stl_algobase.h文件包含在stl_vector.h之后,fill函数的实现在stl_vector.h

    文件中将不可见!

    结论:

    1.头文件的包含必须严格按照顺序,否则结果将难以预料!

    2.你不应该直接使用stl_vector.h文件,而应该使用vector头文件!

  • 相关阅读:
    [置顶] 2013年工作中遇到的20个问题(Bug):161-180
    Spring 3.1.1使用Mvc配置全局日期转换器,处理日期转换异常
    Java中ThreadLocal模拟和解释
    平衡
    一步一步学数据结构之1--n(二叉树遍历--非递归实现)
    RobotFramework+Selenium2环境搭建与入门实例
    UVA10168
    ubantu系统Django安装教程
    The connection to adb is down, and a severe error has occured完整解决办法
    服务端分页
  • 原文地址:https://www.cnblogs.com/zjfdlut/p/1876409.html
Copyright © 2011-2022 走看看