c ++ :. cpp

时间:2019-05-13 12:35:32

标签: c++ windows visual-studio namespaces

我是c ++的新手,遇到了以下代码:

File.h

namespace Type
{
   typedef BOOL (WINAPI *TYCopyFile)
   (
    PCHAR lpExistingFileName,
    PCHAR lpNewFileName,
    BOOL  bFailIfExists
   );
}

namespace Func
{
  extern Types::TYCopyFile pCopyFileA;
}

File.cpp

namespace Funcs
{
  Types::TYCopyFile pCopyFileA;
}

void Init
{
  Funcs::pCopyFileA = (Types::T_CopyFile) GetProcAddress(hKernel32, "CopyFileA");
}

这个想法很简单。我有typedefTypes)的命名空间,并在另一个命名空间(Funcs)中创建了函数指针作为extern。然后,在File.cpp函数的Init中定义该函数指针。

我的问题是,为什么我需要在namespace Funcs中重新声明File.cpp?为什么我不能只拥有Init函数来初始化Funcs::pCopyFileA?据我了解extern,它告诉编译器该变量存在于某处,并告诉链接器找到它。为什么在namespace Funcs中没有File.cpp的链接器找不到它?

1 个答案:

答案 0 :(得分:1)

对于C ++中的所有符号,您都需要一个声明和一个定义。头文件包含Func::pCopyFileA的声明,源文件包含定义。

如果您在头文件中定义了变量(即删除了extern关键字),则将在所有包含头文件的translation units中进行定义。这会破坏one definition rule,并且在链接时会导致多定义错误。