2014-12-17 10 views
5

Ich habe die gleiche Funktion mit dem einzigen Unterschied, dass es entweder erhöht oder dekrementiert. Ich würde das gerne verallgemeinern.Übergeben Inkrement/Dekrement-Operator zu einer Funktion

template<typename O> 
void f(int& i, O op){ 
    op(i); 
} 

int main() { 
    int i; 
    f(i,operator++); 
    f(i,operator--); 
    return 0; 
} 

Wie kann ich das funktionieren lassen?

Meine andere Option ist die Verwendung von funktional std :: plus oder zwei Funktionen, aber ich würde diese Lösung bevorzugen, wenn möglich. Vielen Dank.

+3

einfach Ihre eigenen schreiben Funktor. (Wenn Sie dies tun könnten, indem Sie einfach 'operator ++' schreiben, dann würden Sie 'std :: plus' nicht brauchen ...) –

+0

Ich glaube nicht, dass Sie das für native Typen machen können. –

+5

'f (i, [] (int & v) {++ v;});' – cdhowie

Antwort

6

Verwenden Sie einfach ein Lambda:

template<typename O> 
void f(int& i, O op){ 
    op(i); 
} 

int main() { 
    int i; 
    f(i,[] (int& x) { ++x; }); 
    f(i,[] (int& x) { --x; }); 
    return 0; 
} 

Auch ist es nicht klar, ob Sie post- oder Vorinkrement wollen.

Wie von @ T.C. Wenn Sie die Semantik des normalen Operators beibehalten möchten, können Sie die return-Anweisung hinzufügen.

1

ist hier eine Option (es gibt viele mögliche Lösungen), die auch Pre-C++ 11 funktioniert:

enum OpType { increment, decrement }; 

template <OpType op> void f(int &i); 
template<> void f<increment>(int &i) { ++i; } 
template<> void f<decrement>(int &i) { --i; } 

Verbrauch: wollen

f<increment>(i); 

Damit Ihr Code-Basis ordentlich Sie wahrscheinlich Verwenden Sie jedoch ein gewisses Scoping, verwenden Sie also entweder eine Bereichsaufzählung in C++ 11 oder einen Namespace.

1

im Anwendungsfall Sie geben, ist Typname O eine einstellige Funktion ohne Staat, der mit einem einfachen Funktionszeiger modelliert werden kann:

#include <iostream> 

int& increment(int& i) { 
    ++i; 
    return i; 
} 

int& decrement(int& i) { 
    --i; 
    return i; 
} 

template<typename O> 
void f(int& i, O op){ 
    op(i); 
} 

using namespace std; 

int main() 
{ 
    int i = 0; 
    f(i, increment); 
    cout << i << endl; 

    f(i, decrement); 
    cout << i << endl; 
    return 0; 
} 

Ausgang:

1 
0