C++:错误LNK2019:函数_main中引用的未解析外部符号

C++: error LNK2019: unresolved external symbol referenced in function _main

本文关键字:外部 符号 引用 LNK2019 错误 函数 main C++      更新时间:2023-10-16

我有一些C++代码。

Bird.h

class Bird
{
std::string s;
static int i;
public:
Bird();
~Bird();
friend std::ostream& operator<<(std::ostream& os, Bird& b);
};

Bird.cpp

#include <iostream>
#include <sstream> 
#include "Bird.h"

Bird::Bird()
{
++i;
std::stringstream ss;
ss<<"Bird#";
ss<<i;
s = ss.str();
}
Bird::~Bird()
{
i--;
}
std::ostream& operator<<(std::ostream& os, Bird& b)
{
const char* chr = (b.s).c_str();
return os << chr << std::endl;
}

主要.cpp

#include <iostream>
#include <sstream> 
#include "Bird.h"

int Bird::i=0;
int main()
{
Bird b();
std::cout << b;
}

我得到以下错误:

Main.obj : error LNK2019: unresolved external symbol "class Bird __cdecl b(void)" (?b@@YA?AVBird@@XZ) referenced in function _main

但如果我创建了Bird b;,那没关系。我能做什么?

您打算编写Bird b;来创建Bird对象。

Bird b()是一个函数(称为b,不带参数并返回Bird),您尚未实现它。

Bird b();

这意味着b是一个不接受参数并返回Bird的函数。然后,您尝试输出此函数的值,但该函数不存在。也许你想要:

Bird b;

这意味着b是应该默认构造的Bird

此触发链接器错误

Bird b();

这是一个名为b的函数的函数声明,按值返回一个Bird。然后使用此处的功能:

std::cout << b;

并且链接器找不到它的实现。你需要

Bird b;   // C++03 and C++11
Bird b{}; // C++11

此外,您应该考虑在Bird.cpp中定义Bird::i,而不是在main.cpp中定义。

试试这个:

int main()
{
Bird b;
std::cout << b;
}

默认构造函数不需要"()">

这是C++的"Most Vexing Parse"的一个例子

C++编译器认为您正在声明一个名为b的函数,该函数返回一个Bird,然后尝试打印指向它的指针,而不是默认构造Bird的实例。链接器然后抱怨没有名为b的函数返回Bird。这就是这个错误消息试图告诉你的:

error LNK2019: unresolved external symbol "class Bird __cdecl b(void)" 

在C++语言中,Most Vexing Parse是由于语法歧义而发生的。之所以存在歧义,是因为构造函数调用的语法看起来很像函数原型的语法。

的方式解决的模糊性保证了生成StackOverflow问题,该问题与C保持了一些脆弱的向后兼容性,而牺牲了C++程序中明显的意义。

在这种情况下,因为Bird是默认构造的,所以您可以简单地删除括号,然后就可以完成了。如果你需要调用不同的构造函数,那么上面链接的维基百科文章中的建议可能会有所帮助。

如果您可以使用C++11,您可以使用大括号初始值设定项语法使其始终明确:

Bird b{};             // Use this if default constructed
Bird b{ ..args.. };   // Use this if you need to invoke a particular constructor

最Vexing解析是一个非常丰富的主题。如果你真的很好奇,就用谷歌搜索一下,读一读再读

如果其他操作无效,请检查文件路径是否不包含特殊字符。在添加了一个额外的源文件后,这突然成为了我的一个问题。