Virgule flottante clés dans std:carte

Le code suivant est censé trouver la clé 3.0dans un std::map qui existe. Mais en raison de la précision en virgule flottante, il ne sera pas trouvé.

map<double, double> mymap;
mymap[3.0] = 1.0;

double t = 0.0;
for(int i = 0; i < 31; i++)
{
  t += 0.1;
  bool contains = (mymap.count(t) > 0);
}

Dans l'exemple ci-dessus, contains sera toujours false.
Ma solution actuelle est il suffit de multiplier t de 0,1 au lieu de l'ajout de 0,1, comme ceci:

for(int i = 0; i < 31; i++)
{
  t = 0.1 * i;
  bool contains = (mymap.count(t) > 0);
}

Maintenant, la question:

Est-il un moyen d'introduire un fuzzyCompare à la std::map si j'utilise double clés?
La solution commune pour nombre à virgule flottante comparaison est généralement quelque chose comme a-b < epsilon. Mais je ne vois pas de moyen simple de le faire avec std::map.
Dois-je vraiment d'encapsuler le double type dans une classe et écraser operator<(...) pour mettre en œuvre cette fonctionnalité?

  • Comment fermer est assez proche? Il semble que vous pourriez réellement envie de les stocker et de rechercher via arrondie clés.
  • Dans une sorte de revers pour votre solution de contournement, et si les chars sont tous d'un niveau spécifié de chiffres de précision, vous pouvez stocker les clés que les entiers, les valeurs à virgule flottante être multiplié par certains facteur d'échelle et stockés comme ça.
  • J'ai pensé à ça, mais je vais avoir des problèmes en fonction de la résolution je risque de débordement facilement.
  • Vous devez être conscient que même votre solution de contournement peut échouer - vous eu de la chance sur l'arrondissement pour la multiplier. 0.1 ne peut pas être représenté précisément en base 2.
  • oui, je sais. C'est pourquoi je voulais une vraie solution. Mais vous devez admettre, c'est un bel exemple pour montrer comment float comparaisons peuvent conduire à un comportement indéterminé. 🙂
  • Voir stackoverflow.com/questions/4816156/...
  • Votre code fonctionne correctement. Lorsque vous ajoutez le double 0.1 à lui-même dix fois, vous n'obtenez pas 1.0.
  • Dans votre cas, vous devriez sans doute utilisés "point fixe" les clés. double peuvent utilement être utilisé comme une clé dans une carte lorsque vous envisagez de l'utiliser pour l'interpolation ou de faire un histogramme. Pour l'un de ces, vous allez utiliser lower_bound à définir la gamme d'une valeur de chutes et à quelle distance entre les limites, il tombe.

InformationsquelleAutor pokey909 | 2011-07-13