在 Map.h 文件的以下代码中没有识别国家或大陆的问题
map .h:
#ifndef MAP_H
#define MAP_H
#include<string>
#include<vector>
#include<iostream>
#include<fstream>
//#include "Country.h"
using namespace std;
class Map{
private:
vector<Country> countries;
vector<Continent> continents;
vector<vector<int> > adjacents;
string author;
string image;
string wrap;
string scroll;
string warn;
public:
Map(ifstream);
Map();
void save();
void setAdjacent(Country&, Country&);
void placeWithin(Continent&, Country&);
int numOfCountries();
int numOfContinents();
bool verify();
bool isAdjacent(Country*, Country&);
bool hasAdjacent(Country*);
bool hasCountry(Continent&);
};
#endif
是否在注释掉的include中添加,还是报错。
这是另外两个文件
大陆.h:
#ifndef CONTINENT_H
#define CONTINENT_H
#include "Map.h"
using namespace std;
class Continent
{
private:
string name;
int bonus;
vector<Country> countries;
public:
void addCountry(Country&);
int getOwner();
int getBonus();
int getSize();
string getName();
bool hasCountry(Country&);
};
#endif
国家.h:
#ifndef COUNTRY_H
#define COUNTRY_H
#include "Continent.h"
using namespace std;
class Country{
private:
static int nextCountryNumber;
int countryNumber;
Map map;
string name;
int x, y;
Continent continent;
vector<Country> adjacents;
public:
Country(string, int, int, Continent&, Map&);
string getName();
int getX();
int getY();
Continent getContinent();
bool isAdjacentTo(Country&);
bool hasAdjacent();
void addAdjacent(Country&);
string toString();
};
#endif
我认为它是某种循环引用,但我找不到这种情况...
最佳答案
通常在 .h 文件中您不希望包含其他头文件。它们只是声明,所以它们不需要知道其他类是什么样子的。删除 #include "blah.h"
而是写前向声明 class blah;
你需要它们的地方。这是这种情况除非您存储一个对象blah
直接在你的类里面,在这种情况下你需要包括blah.h
因为编译器需要知道那个对象有多大。如果您存储指向对象的指针而不是直接存储对象,则可以避免这些包含(实际上这是一种更常见的做法,因为在复制构造时不需要复制所有数据)。
编辑:作为旁注,您通常只想包括必要的 #includes
(即 iostream),也不使用 using namespace std;
在你的标题中,因为包含你的标题的另一个文件可能不想使用 std 命名空间。相反,在您的实现文件中执行这些操作。我在下面做了相应的更改。
编辑 2:另外,请记住 map
是 std 中的数据结构类型,所以命名时要小心 map
(我建议使用不同的名称)。
编辑 3:正如评论中所指出的,std 容器需要完整声明它们所包含的对象,所以无论何时你有 vector<blah>
你必须包括 blah.h
.还要考虑这一点:包含对象 blah
是有问题的在自己的声明中。既然对象包含了它自己的一个实例,那是递归的,那么应该分配多少空间呢?你可以通过 pointer-to-blah
来解决这个问题在 blah
(指针只是一个固定大小的 int)。出于类似的原因,Country
也有问题包含 vector<Country>
的类.这可以通过更改 vector<Country>
来解决至 vector<Country*>
.因此,为了使这些在技术上可由 C++ 标准编译并清理关于包含其他 header 的设计,我更改了引用 Country
的成员变量。 , Continent
, 和 Map
指向它们各自的指针,您需要在实现文件中反射(reflect)这一变化。我也修改了 Map(std::ifstream);
至 Map(std::ifstream &);
正如另一条评论所建议的那样,我严重怀疑您打算在此处复制 ifstream。
代码:
map .h:
#ifndef MAP_H
#define MAP_H
#include<string>
#include<vector>
#include<fstream>
class Country;
class Continent;
class Map{
private:
std::vector<Country*> countries; // consider pointers instead
std::vector<Continent*> continents; // consider pointers instead
std::vector<std::vector<int> > adjacents; // (just ints, so no pointers needed)
std::string author;
std::string image;
std::string wrap;
std::string scroll;
std::string warn;
public:
Map(std::ifstream &);
Map();
void save();
void setAdjacent(Country&, Country&);
void placeWithin(Continent&, Country&);
int numOfCountries();
int numOfContinents();
bool verify();
bool isAdjacent(Country*, Country&);
bool hasAdjacent(Country*);
bool hasCountry(Continent&);
};
#endif
大陆.h:
#ifndef CONTINENT_H
#define CONTINENT_H
#include<string>
#include<vector>
class Country;
class Continent
{
private:
std::string name;
int bonus;
std::vector<Country*> countries;
public:
void addCountry(Country&);
int getOwner();
int getBonus();
int getSize();
std::string getName();
bool hasCountry(Country&);
};
#endif
国家.h:
#ifndef COUNTRY_H
#define COUNTRY_H
#include<string>
#include<vector>
class Map;
class Continent;
class Country{
private:
static int nextCountryNumber;
int countryNumber;
Map *map;
std::string name;
int x, y;
Continent *continent;
std::vector<Country*> adjacents;
public:
Country(std::string, int, int, Continent&, Map&);
std::string getName();
int getX();
int getY();
Continent getContinent();
bool isAdjacentTo(Country&);
bool hasAdjacent();
void addAdjacent(Country&);
std::string toString();
};
#endif
关于c++ - 未识别的标识符 c++,但已识别,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/33536047/