2017-07-25 | 研究与探索 | UNLOCK

VC++的一个BUG

最近用c++解决八皇后问题,定义了一个chessboard类,类中定义了友元operator<<使其能用cout输出。 在 chessboard.h 中就是这样:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
#ifndef CHESSBOARD_H
#define CHESSBOARD_H

#include <ostream>
using namespace std;

...

class chessboard{
private:

...

public:
...
friend ostream & operator<<(ostream &o,const chessboard &chb);
};
ostream & operator<<(ostream & o,const chessboard &chb)
{
...
}

#endif

但老是编译不过, LINK2005 错误什么的。

百度之,都建议把友元函数的定义直接写在类声明里,我试了试的确可以解决这个问题。

有人说是using namespace std语句的问题,但当我把各文件中#include "chessboard.h"放在using语句的后面,问题依然存在。 后来我将operator<<的定义单独放在 chessboard.cpp 中,也能编译过。 这真是个BUG,预处理器处理后应该只有一份operator<<的定义,但显然VS进行了某些奇怪的优化,造成了混乱,#ifndef都没用,而且经试验用#pragma once也不行。

————————20180304 更新————————

我错怪VS了……我在两个.cpp文件中 include 了 chessboard.h ,又没有将operator<<声明为静态或内联,当然会有两份可外链接的operator<<定义从而产生冲突……