2009-07-21 21 views
7

Jestem zdezorientowany co do tego, co wywołuje :: bind, gdy wiążemy ze zmiennymi składowymi. Z wiązaniem do funkcji składowej, w zasadzie tworzymy obiekt funkcji, a następnie wywołujemy przekazywanie do niego argumentów, które są dostarczane lub opóźniane i zastępowane przez placeholder.Powiązanie ze zmienną składową

Ale co to wyrażenie ma za kulisami:

boost::bind(&std::pair::second, _1); 

Co dostaje podstawionych w miejsce zastępczy _1?

Znalazłem to podczas czytania tego przykładu z artykułu na boost :: wiąże:

void print_string(const std::string& s) { 
    std::cout << s << '\n'; 
} 

std::map<int,std::string> my_map; 
my_map[0]="Boost"; 
my_map[1]="Bind"; 

std::for_each(
    my_map.begin(), 
    my_map.end(), 
    boost::bind(&print_string, boost::bind(
     &std::map<int,std::string>::value_type::second,_1))); 

source

Odpowiedz

4

Za kulisami jest za pomocą wskaźnika członkiem i stosując ją do przekazany w argument. Jest to dość skomplikowane w kontekście powiązań, więc o to prosty przykład wskaźnik do użycia użytkownik:

int main() 
{ 
    std::pair< int, int > p1 = make_pair(1, 2); 
    std::pair< int, int > p2 = make_pair(2, 4); 
    int std::pair<int,int>::*ptr = &std::pair<int,int>::second; // pointer to second member 

    std::cout << p1.*ptr << std::endl; // 2 dereference pointer to member 
    std::cout << p2.*ptr << std::endl; // 4 dereference pointer to member 
} 

Za kulisami wiązać się komponować różne połączenia. Wynikowy funktor pobiera dereferencje std :: map <> :: iterator (typu std :: pair < const klucz_typ, value_type>). Zostało to przekazane do wewnętrznego powiązania, które usuwa zaznaczenie wskaźnika członkowskiego, zwracając w ten sposób (*it).second do zewnętrznego powiązania, które przekazuje tę wartość do metody dla końcowego wywołania: print_string((*it).second).

(*it) to rzeczywiście numer _1, o który pytałeś. Wszystkie _# są symbolami zastępczymi, tzn. Wynikiem powiązania będzie funktor, który pobierze tyle argumentów, ile różnych symboli zastępczych istnieje w kolejności określonej przez liczbę symboli zastępczych. W podanym przykładzie uzyskany funktor przyjmuje jeden argument: _1.

2
boost::bind(&std::pair<U,V>::second, _1); 

funkcjonalnie równoważne

std::pair<U,V> p -> p.second 

tj. jest funkcją (obiektem), która odwzorowuje numer pair<U,V> na swój element second.

Powiązane problemy