如何在C++中解决这些名称冲突?

mis*_*why 3 c++ compiler-construction linker conflict

说我有这种物理结构:

/
  +-- conflicttest
  |     +-- A.cpp
  |     +-- A.h
  |     +-- main.cpp
  +-- libconflict
  |     +-- conflict
  |     |     +-- A.h
  |     |     +-- B.h
  |     +-- A.cpp
  |     +-- B.cpp
Run Code Online (Sandbox Code Playgroud)

这些是libconflict的来源,深呼吸:

class B libconflict中的标头:

// libconflict B.h
class B
{
public:
    void bar();
protected:
    int j_;
};
Run Code Online (Sandbox Code Playgroud)

class B libconflict中的实现:

// libconflict B.cpp
#include "conflict/B.h"

void B::bar()
{
    std::cout << "B::bar" << std::endl;
}
Run Code Online (Sandbox Code Playgroud)

class A libconflict中的标头:

// libconflict A.h
# include "conflict/B.h"

class A : public B
{
public:
    A();
private:
    int i_;
};
Run Code Online (Sandbox Code Playgroud)

class A libconflict中的实现:

#include "conflict/A.h"

A::A()
{
    std::cout << "libconflict A is alive" << std::endl;
    i_ = 51; // some random fields and values... I should admit I am lost
    j_ = 47;
}
Run Code Online (Sandbox Code Playgroud)

现在冲突的根源,它几乎结束了:

class A 冲突中的标题:

// conflicttest A.h
class A
{
public:
    A();
    void foo();
};
Run Code Online (Sandbox Code Playgroud)

class A 在conflictttest中实现:

// conflicttest A.cpp
#include "A.h"

A::A()
{
    std::cout << "A is alive" << std::endl;
}

void A::foo()
{
    std::cout << "A::foo" << std::endl;
}
Run Code Online (Sandbox Code Playgroud)

最后,main.cpp:

// main.cpp in conflicttest
#include "conflict/A.h"

int main()
{
    B* b = new A;
    b->bar();
return 0;
}
Run Code Online (Sandbox Code Playgroud)

Phew ...我正在使用Visual Studio 2010来构建此解决方案.conflicttest是一个与静态库链接的可执行文件libconflict.这个编译就像一个魅力,不管你信不信,输出是:

A is alive
B::bar
Run Code Online (Sandbox Code Playgroud)

链接器实际使用的符号A来自conflicttest这绝对不是B更糟的是,它可以调用B::bar().

我迷路了,为什么编译器不抱怨?

Mar*_*som 6

您违反了" 一个定义规则".

编译器没有抱怨,因为它在跨越翻译单元边界时可以检测到的东西是有限的.