std :: map有什么用呢?

时间:2016-09-25 18:44:25

标签: c++

任何人都可以使用std::map解释我从这个简单程序中获得的输出。请注意,我将p插入到地图中,但不是q,但它说它们都找到了它们,但也说地图中只有1个元素!

#include <map>
#include <iostream>

struct screenPoint {
  float x = 0, y = 0;
  screenPoint(float x_, float y_): x{x_}, y{y_}{}
};

bool operator<(const screenPoint& left, const screenPoint& right){
  return left.x<right.x&&left.y<right.y;
}

std::map<screenPoint, float> positions;

int main(int argc, const char * argv[]) {

  auto p = screenPoint(1,2);
  auto q = screenPoint(2,1);
  positions.emplace(p,3);

  auto f = positions.find(p);
  auto g = positions.find(q);

  if (f == positions.end()){
    std::cout << "f not found";
  } else {
    std::cout << "f found";
  }

  std::cout << std::endl;

  if (g == positions.end()){
    std::cout << "g not found";
  } else {
    std::cout << "g found";
  }

  std::cout << std::endl;

  std::cout << "number elements: " << positions.size() << "\n";
  return 0;
}

输出:

f found
g found
number elements: 1

2 个答案:

答案 0 :(得分:5)

问题在于您在这种情况下定义比较仿函数的方式。这两个元素pq具有相同的xy,只是反转。 您的逻辑检查一个的x小于另一个的y,以及true。对于这些输入,这永远无法评估为int main() { auto p = screenPoint(1,2); auto q = screenPoint(2,1); std::cout << std::boolalpha << (p < q) << " " << (q < p) << std::endl; }

试试这个代码段:

false false

它会打印出来

p

因此q不小于qp不小于namespace AppBundle\Entity; use Doctrine\ORM\Mapping as ORM; /** * @ORM\Entity * @ORM\Table(name="album") */ class Album { 。就地图而言,这使它们等同。

答案 1 :(得分:3)

为了在std::map中使用数据类型,它必须具有称为严格弱排序(https://en.wikipedia.org/wiki/Weak_ordering)的特定排序。这意味着不等式运算符(<)遵循一组非常具体的规则。但是,您指定的运算符不是弱排序。特别是,给定两个screenPoint s,ab分别由(1,2)和(2,1)构造,您将看到{{1}那个a < b。在严格的弱排序中,这需要暗示b < a,这不是真的!

因为你的不等式算子不符合严格弱序的要求,a == b最终会做出意想不到的事情。我建议阅读有关这种排序的更多细节,并阅读/思考地图需要它的原因。在短期内,您可以按如下方式重新定义您的运营商:

map