2009-09-09 9 views
7

J'ai posé une question il y a longtemps about accessing the underlying container of STL adapters. Je suis très utile réponse:Je ne comprends pas cette ligne - déréférencer une adresse de variable membre privé ou quoi?

template <class T, class S, class C> 
    S& Container(priority_queue<T, S, C>& q) { 
     struct HackedQueue : private priority_queue<T, S, C> { 
      static S& Container(priority_queue<T, S, C>& q) { 
       return q.*&HackedQueue::c; 
      } 
     }; 
    return HackedQueue::Container(q); 
} 

int main() 
{ 
    priority_queue<SomeClass> pq; 
    vector<SomeClass> &tasks = Container(pq); 
    return 0; 
} 

Malheureusement, je ne pouvais pas comprendre cette ligne:

return q.*&HackedQueue::c; 

Qu'est-ce que cette ligne fait? En outre, comment cette ligne peut-elle accéder au conteneur privé priority_queue qui est transmis à la fonction Container?

+0

@curtisk Merci de corriger mon titre :) – AraK

+0

Je pense que vous voudrez peut-être lire sur mon entrée légèrement "sarcastique des fonctionnalités cachées de C++": http://stackoverflow.com/questions/75538/hidden-features-of- c/1065606 # 1065606 :) –

+0

@Alcon, Man ma réponse n'était pas vraiment bonne, je préférais l'effacer, j'apprécie l'homme :) – AraK

Répondre

12

Pensez comme ceci:

(q).*(&HackedQueue::c); 

Tout d'abord, vous avez HackedQueue :: c, qui est juste le nom d'une variable membre. Ensuite, vous prenez & HackedQueue :: c, qui est un pointeur vers cette variable membre. Ensuite, vous prenez q, qui est juste une référence d'objet. Ensuite, vous utilisez l'opérateur "Lier le lien au membre par référence" .* pour lier la variable membre référencée par le pointeur de variable de membre en utilisant q comme this. En ce qui concerne le numéro de membre privé, priority_queue::c est seulement protégé, pas privé, il n'est donc pas surprenant que lorsque vous dérivez de priority_queue, vous pouvez accéder à ses membres protégés.

+0

Merci mais 'c' est une variable membre. Quel est le conteneur à l'intérieur de std :: priority_queue. – AraK

+0

Désolé, oui. C'est une variable membre, mais la liaison à l'opérateur membre est toujours la même (tout comme '. 'Est utilisé pour les deux tâches.) – Eclipse

+0

Belle explication +1 – AraK

Questions connexes