我正在设置一个 unordered_map,其中键是 Direction 的枚举,定义为:
enum Direction : uint16_t {
North = 1 << 0,
East = 1 << 2,
South = 1 << 3,
West = 1 << 4,
None = 1 << 5,
};
目标是检查是否至少设置了 2 个标志,但最多设置了 n 标志。
通过上面定义的枚举,我尝试创建许多 unordered_maps
std::unordered_map<Direction, std::vector<Tile*>>* groundTiles;
std::unordered_map<Direction, std::vector<Tile*>>* northEastHillTiles;
std::unordered_map<Direction, std::vector<Tile*>>* southEastHillTiles;
std::unordered_map<Direction, std::vector<Tile*>>* platformTiles;
std::unordered_map<Direction, std::vector<Tile*>>* wallTiles;
我将它们初始化为
groundTiles = new std::unordered_map<Direction, std::vector<Tile*>>();
groundTiles->insert_or_assign(Direction::None, std::vector<Tile*>());
groundTiles->insert_or_assign(Direction::East, std::vector<Tile*>());
groundTiles->insert_or_assign(Direction::West, std::vector<Tile*>());
groundTiles->insert_or_assign((Direction)(Direction::East|Direction::West),std::vector<Tile*>());
and so on for the other sets
但是,当我尝试从地面(或任何其他集合)拉出一个图块时,我无法检查是否至少设置了 Direction::East 和 Direction::West 。 我试过了:
Tile* westAndEastCapped = southEastHillTiles->at((Direction)(Direction::West | Direction::East)).at(0);
但它似乎只是默认为 Direction::East 设置。
如何从无序地图中选择一个图块,同时设置了东部和西部标志,而没有其他标志?
这不是
std::unordered_map::at()
的工作原理。它仅从无序映射中检索与传入参数等于的键的值。相当于“完全”。就是这样。没有别的了。
此外,如果指定的键不存在,
at()
会抛出异常。
std::unordered_map
知道它的关键是它是某种不透明的值。 std::unordered_map
不关心密钥的任何解释或含义,除了 std::unordered_map
对其密钥的唯一要求是它具有相等性比较并且具有哈希函数。
enum
满足这些要求。结束。仅仅因为这个特定的 enum
被解释为某种位掩码,对于 std::unordered_map
来说没有任何意义。
A
std::unordered_map
不太适合您尝试访问其值的方式,它不会起作用。您可能需要为您的值设计一个自定义容器,以有效地实现所需的访问模式。
在最坏的情况下,你总是可以诉诸范围迭代:
for (auto &[key, value]: southEastHillTiles)
{
// ...
}
然后检查地图中存在的每个
key
,以确定它是否符合您要搜索的内容。这是非常低效的,但这几乎是 unordered_map
可以完成的唯一事情。