我有一个结构
struct key { int x; int y; int z; };
比如x,y,z可以取1到10之间的值.
我也有一张地图
std::mapmyMap;
我用不同的键值填充.
有没有办法循环遍历所有键值,例如z = 5.那是(就伪代码而言)
loop over myMap double v += myMap.find({x=anything,y=anything,z=5})->second;
如果有人可以提供一些关于这是否可以实现的评论(我不想使用增强容器),那将是非常友好的.
标准关联容器使用一维排序,即它们只知道一个键是否小于,等于或大于另一个.所以这不是有效的.您可以使用线性时间实现此类过滤std::find_if()
.
O(log n)
然而,维持查找时间,可以使用不同的索引方法创建多个映射; 例如一个用X,一个用Y,一个用Z作为关键.如果值是大对象,则可以使用指针不必不必要地复制它们.当然,这可以全部隐藏在封装类之后,它为外部提供基于轴的排序.
对于小空间(例如x,y,z从1到10)合理的另一种方法是不使用std::map
3D阵列/矩阵.这可以使用1D std::vector
,通过将索引从3维映射到1来实现.
如果key
先使用z 对struct进行排序,可以这样做:
bool operator<( const key &k1, const key &k2 ) { return std::make_tuple( k1.z, k1.x, k1.y ) < std::make_tuple( k2.z, k2.x, k2.y ); // z must be first } auto min = std::numeric_limits::min(); auto end = map.lower_bound( key{ min, min, 6 } ); for( auto it = map.lower_bound( key{ min, min, 5 } ); it != end; ++it ) { ... }
但如果您需要迭代x或y,则必须为每个坐标创建单独的多图,并指向结构或使用指针boost::multiindex
.