2010-07-27 7 views
3

Je définis un type d'itérateur qui ne stocke pas explicitement sa valeur actuelle. Au lieu de cela, il s'agit d'un wrapper autour d'un autre itérateur et renvoie std::pair s des valeurs de l'itérateur sous-jacent et une autre valeur. La partie pertinente de la définition de classe:Comment surcharger l'opérateur-> sur un itérateur "générateur"?

class MyIterator : public std::iterator<input_iterator, std::pair<Foo *, Bar *> > { 

    FooPtrIterator d_iter; 
    Bar d_bar; 

    public: 

     MyIterator(FooPtrIterator iter, Bar const &bar) 
     : 
      d_iter(iter), 
      d_bar(bar) 
     { } 

     // Returning by value, not storing the pair itself. 
     value_type operator*() const { 
      return std::make_pair(*d_iter, &d_bar); 
     } 

     // Can't return by value! 
     ??? operator->() const { 
      return ???; 
     } 

}; 

Maintenant, cela me met en difficulté en cas de surcharge operator->, parce que je suis attendu à retourner un pointeur, ou autre chose qui se prend en charge operator->.

Je ne pouvais stocker le std::pair actuel en tant que membre de la classe:

value_type d_current; 

Cependant, qui me fait des ennuis dans le constructeur, parce que je ne peux pas savoir à ce moment si FooPtrIterator iter est un itérateur valide, donc je ne peut pas le déréférencer pour fournir d_current avec une valeur.

Je peux également faire operator-> retourner un boost::shared_ptr<value_type> mais c'est un hack terrible avec plus de frais généraux que devrait être nécessaire. J'ai l'impression que cet itérateur "générateur" n'est pas censé exister. Est-ce vrai ou existe-t-il un autre moyen de contourner cela?

Répondre

2

Je suggère la création d'une propre classe tenant Foo * et bar paire *, comme ceci:

class MyPair { 
private: 
    FooPtrIterator foo; 
    Bar bar; 

public: 
    MyPair(const FooPtrIterator& it, const Bar& b) : foo(it), bar(b) {} 

    Foo* first() { return *foo; } 
    Bar* second() { return &bar; } 
}; 

Ensuite, il suffit d'utiliser à l'intérieur de votre classe itérateur au lieu des deux valeurs. Vous devrez changer -> first et -> second à -> first() et -> second() dans votre code mais cela devrait être un changement acceptable.

+0

C'est une bonne solution, et aussi simple que possible. Merci! – Thomas

Questions connexes