“position”在C ++中是一个保留字吗?

时间:2012-02-24 10:18:58

标签: c++ visual-c++

这是我编写的代码的简化版本:

#include <iostream>

class pos
{
    public:
        char (&board)[64];
        pos(char (&arr)[64])
            : board(arr)
        {
            *board = *arr;
        }
        void print();
};

void pos::print()
{
    for (int y=0; y<8; y++)
    {
        for (int x=0; x<8; x++)
            std::cout << (int) board[x + y*8] << " ";
        std::cout << "\n";
    }
}

int main()
{
    char test[64] = {
        0, 1, 2, 3, 4, 5, 6, 7,
        1, 2, 3, 4, 5, 6, 7, 8,
        2, 3, 4, 5, 6, 7, 8, 9,
        3, 4, 5, 6, 7, 8, 9,10,
        4, 5, 6, 7, 8, 9,10,11,
        5, 6, 7, 8, 9,10,11,12,
        6, 7, 8, 9,10,11,12,13,
        7, 8, 9,10,11,12,13,14 };

    pos p(test);
    p.print();

    std::cin.get();
    return 0;
}

但如果我将pos的所有实例更改为position,我会收到错误:main.obj:错误LNK2005:&#34; public:void __thiscall position :: print(void)& #34; (?print @ position @@ QAEXXZ)已在position.obj中定义 1&gt; D:\ Programming \ Test \ Debug \ Test.exe:致命错误LNK1169:找到一个或多个多重定义的符号

奇怪的是,该类曾经被命名为position并且编译得很好,直到我对它处理board数组的方式做了一些更改。有人可以解释为什么我会收到此错误吗?

更新

现在,这个类的命名并不重要,我得到了同样的错误。我创建了一个新的MSVC ++项目,复制了源文件,并进行了新的构建。同样的错误。这是实际的代码,而不是简洁的版本。

的main.cpp

#include <iostream>
#include "position.cpp"

int main()
{
    char test[64] = {               // Simple mate test position; TODO: move to test suite
        OO,BK,OO,OO,OO,OO,OO,OO,
        OO,OO,OO,OO,OO,OO,OO,WR,
        OO,WK,OO,OO,OO,OO,OO,OO,
        OO,OO,OO,OO,OO,OO,OO,OO,
        OO,OO,OO,OO,OO,OO,OO,OO,
        OO,OO,OO,OO,OO,OO,OO,OO,
        OO,OO,OO,OO,OO,OO,OO,OO,
        OO,OO,OO,OO,OO,OO,OO,OO };

    position pos(test);
    pos.print();

    std::cin.get();

    return 0;
}

position.cpp

#include <iostream>

// Board-centric representation; pass as 64-byte array

#define WK 0x0  // White King   
#define WQ 0x1  // White Queen
#define WR 0x2  // White Rook
#define WB 0x3  // White Bishop
#define WN 0x4  // White Knight
#define WP 0x5  // White Pawn
#define BK 0x6  // Black King
#define BQ 0x7  // Black Queen
#define BR 0x8  // Black Rook
#define BB 0x9  // Black Bishop
#define BN 0xA  // Black Knight
#define BP 0xB  // Black Pawn
// 0xC: unused
// 0xD: unused
// 0xE: unused
#define OO 0xF  // Empty

class position
{
    public:
        char (&board)[64];
        position(char (&arr)[64])   // TODO: 'board' dies if the variable passed through 'arr' dies. Allocating memory might fix this. See 'new' and 'shared_ptr'.
            : board(arr)
        {
            *board = *arr;
        }
        void print();
};

void position::print()
{
    for (int y=0; y<8; y++)
    {
        for (int x=0; x<8; x++)
            std::cout << (int) board[x + y*8] << " ";
        std::cout << "\n";
    }
}

(我正在写一个程序来弄清楚简单的国际象棋游戏结束。)

正如您所看到的,position::print()仅在一个地方定义,与错误消息相反......除非我严重忽视某些内容。这很早。

6 个答案:

答案 0 :(得分:2)

您不应该在主文件中#include "position.cpp",而应该是position类的头文件。

答案 1 :(得分:2)

问题是您正在编译position.cpp 中包含的代码,并且您正在尝试将已编译的代码链接到一个文件中。

问题是由main.cpp中的这一行引起的:

#include "position.cpp"

您要包含C ++源文件,而不是标题。这意味着position.cpp中的所有代码都包含在main.cpp中,然后编译生成的文件。然后,您可以自己编译position.cpp

尝试包含position.h - 如果还没有这样的标题,请定义它。另一种解决方法是不将position.cpp添加到要编译的源列表中。

答案 2 :(得分:1)

您在main.cpp中包含postition.cpp,可能您的构建系统也单独构建position.cpp,然后链接器会找到您类的多个定义。

你应该制作一个单独的标题并在msvc上添加包含警戒,#pragma once

答案 3 :(得分:0)

错误消息指出您有void position::print()的两个定义,一个位于main.cpp,另一个位于position.cpp

答案 4 :(得分:0)

这不是保留字,而是position.cpp的名称。您使用相同的名称,但在main.cpp中具有不同的含义。

答案 5 :(得分:0)

编译器/链接器处理翻译单元,而不是文件。您可以在一个文件(position.cpp)中定义position :: print。但是,自从您编写#include "position.cpp"以来,该定义实际上存在于两个翻译单元中。您违反了ODR(一个定义规则)。