Question

(Je crois) Je connais la surcharge des fonctions basées sur la constance :si l'instant est const, la méthode const est appelée, sinon la méthode non const.

Exemple (également à idée):

#include <iostream>

struct S
{
  void print() const { std::cout << "const method" <<std::endl };
  void print()       { std::cout << "non-const method" <<std::endl };
};

int main()
{
  S const s1;
  s1.print(); // prints "const method"
  S s2;
  s2.print(); // prints "non-const method"
  return 0;
};

J'ai essayé/essayé de l'utiliser dans mon code, mais j'ai rencontré des problèmes lorsque le const les méthodes surchargées n'ont pas la même catégorie d'accès.C'est peut-être un mauvais style, mais voici un exemple qui reflète l'idée de renvoyer des références pour éviter de copier et d'utiliser const pour limiter les modifications involontaires :

struct Color;
struct Shape
{
  double area;
};

class Geometry
{
public:
  // everybody can alter the color of the geometry, so 
  // they get a mutable reference
  Color& color() { return m_color; };

  // not everybody can alter the shape of the Geometry, so
  // they get a constant reference to the shape.
  Shape const& shape() const { return m_shape; };

protected:
  // derived classes can alter the shape, so they get 
  // access to the mutable reference to alter the shape.
  Shape & shape() { return m_shape; };

private:
  Shape m_shape;
  Color m_color;
};

Le problème auquel je suis confronté maintenant est que je veux que le compilateur récupère le public, const-renvoyer la fonction de forme si une autre fonction perturbe les géométries, par exemple les colorer en fonction de leur zone, pour laquelle cela nécessiterait d'accéder à la forme de la géométrie :

// this one fails
void colorByArea() {
  for( Geometry g : geometryList )
  { g.color() = colorMap[g.shape().area]; }
}

// this one is a clunky workaround
void colorByArea() {
  for( Geometry g : geometryList )
  { 
    Geometry const& g_const = g;
    g.color() = colorMap[g_const.shape().area];
  }
}

Ceci (ou quelque chose de similaire) échoue avec l'erreur suivante assez compréhensible :

‘Shape& Geometry::shape()’ is protected 
  Shape & shape() { return m_shape; };

^ error: within this context
  g.color() = colorMap[g.shape().area];

(J'ai mis un exemple légèrement simplifié sans compilation sur idée.)

Je comprends (dans une certaine mesure) pourquoi cela se produit :g n'est pas const et donc la forme non const (), qui est protectorec, est censée être appelée - mais cela échoue évidemment.

Donc je suppose que mon QUESTION est:Existe-t-il un moyen d'obtenir une sorte de « repli » vers une fonction const si une fonction non const n'est pas accessible ?

Était-ce utile?

La solution

Existe-t-il un moyen d'obtenir une sorte de « repli » vers une fonction const si une fonction non const n'est pas accessible ?

Non;la résolution de la surcharge se produit avant le contrôle d’accès.

Ce n’est pas seulement un mauvais style ;c'est une mauvaise conception.Une fonction getter publique est conceptuellement différent à partir d'une fonction protégée qui permet au code connaissant les éléments internes de modifier l'état interne de l'objet.En général, les deux fonctions n'ont même pas besoin d'avoir des types de retour liés.Ils ne devraient donc pas porter le même nom.

Autres conseils

Vous pouvez utiliser const_cast pour permettre d'appeler la version const comme :

int main()
{
  S s2;
  const_cast<const S&>(s2).print(); // prints "const method"
  return 0;
};

Mais il serait préférable/plus simple de renommer l'une des méthodes.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top