Aufruf der Funktion mit aus der Zeichenkette extrahierten Parametern

7

Ich betrachte das folgende Problem:

Ich bekomme Strings, die wie folgt formatiert sind:

%Vor%

und ich möchte die Funktion mit den gegebenen Parametern aufrufen. Nehmen wir an, ich habe einen Funktionstest:

%Vor%

und ich bekomme eine Nachricht:

%Vor%

Dann möchte ich, dass der Funktionstest automatisch wie folgt aufgerufen wird:

%Vor%

Haben Sie Hinweise, wie Sie dies in C ++ erreichen können?

    
joekr 12.12.2011, 15:52
quelle

5 Antworten

18

Update: stream_function wurde aktualisiert, um das Argument argument-evaluation-order @Nawaz, das in den Kommentaren erwähnt wurde, zu beheben und das std::function zur Verbesserung der Effizienz entfernt. Beachten Sie, dass die Korrektur der Auswertungsreihenfolge nur für Clang funktioniert, da GCC dem Standard hier nicht folgt. Ein Beispiel für GCC mit manueller Befehlserzwingung finden Sie hier .

Dies ist im Allgemeinen nicht so einfach zu bewerkstelligen. Ich habe einmal eine kleine Wrapperklasse um std::function geschrieben, die die Argumente aus einem std::istream extrahiert. Hier ist ein Beispiel mit C ++ 11:

%Vor%

Kompiliert unter Clang 3.3 und funktioniert wie erwartet ( kleines Live-Beispiel ).

%Vor%

Es hat Spaß gemacht, diese Klasse wieder zusammen zu hacken, ich hoffe, Sie genießen es. Beachten Sie, dass Sie den Code ein wenig ändern müssen, damit er für Ihr Beispiel funktioniert, da C ++ - IOstreams Leerzeichen als Trennzeichen haben. Daher müssen Sie alle Unterstriche in Ihrer Nachricht durch Leerzeichen ersetzen. Sollte jedoch einfach zu tun sein, danach einfach ein std::istringstream aus Ihrer Nachricht konstruieren:

%Vor%     
Xeo 12.12.2011, 17:09
quelle
3

Sie können so ziemlich nicht, C ++ hat keine Art von Reflektion über Funktionen.

Die Frage ist dann, wie nahe Sie kommen können. Ein Interface wie dieses ist ziemlich plausibel, wenn es passen würde:

%Vor%

Wo registered_functions ein map<string,std::function<void,string>> ist, und Sie müssen explizit etwas tun wie:

%Vor%

für jede Funktion, die auf diese Weise aufgerufen werden kann.

make_registration wäre dann eine ziemlich haarige Template-Funktion, die einen Funktionszeiger als Parameter nimmt und ein std::function -Objekt zurückgibt, das beim Aufteilen die Zeichenkette in Chunks zerlegt, prüft, ob dort die richtige Zahl ist, konvertiert jede zum korrekten Parametertyp mit boost::lexical_cast und ruft schließlich die angegebene Funktion auf. Es würde den "korrekten Typ" aus dem Template-Argument zu make_registration kennen - um beliebig viele Parameter zu akzeptieren, müsste dies eine C ++ 11 variadische Vorlage sein, aber Sie können es fälschen mit:

%Vor%

Der Umgang mit Überladungen und optionalen Parametern würde zu weiteren Komplikationen führen.

Obwohl ich nichts über sie weiß, erwarte ich, dass es C ++ - Support-Frameworks für SOAP oder andere RPC-Protokolle gibt, die möglicherweise relevanten Code enthalten.

    
Steve Jessop 12.12.2011 16:04
quelle
1

Was Sie suchen, ist Reflexion. Und das ist in C ++ nicht möglich. C ++ ist auf Geschwindigkeit ausgelegt. Wenn Sie die Überprüfung einer Bibliothek oder eines Codes benötigen und dann die darin enthaltenen Typen identifizieren und Methoden aufrufen, die diesen Typen zugeordnet sind (normalerweise Klassen), dann ist dies meiner Ansicht nach in C ++ nicht möglich.

Als weitere Referenz können Sie auf diesen Thread verweisen.

Wie kann ich einer C ++ - Anwendung Reflektion hinzufügen? >

Ссылка

Warum hat C ++ keine Reflektion?

    
Ajai 12.12.2011 16:04
quelle
0

Sie könnten die Zeichenfolge parsen, die Argumente trennen und sie problemlos an die Funktion senden, aber Sie können die Funktion nicht mit ihrem Namen in einer Zeichenfolge referenzieren, da die Funktion zur Laufzeit keinen Namen mehr hat .
Sie könnten eine if-else if-Kette haben, die nach dem Funktionsnamen sucht, und dann die Argumente analysieren und die spezifische Funktion aufrufen.

    
Petruza 12.12.2011 16:04
quelle
0

Ich habe @ Xeos Code so modifiziert, dass er richtig mit gcc arbeitet, damit die Parameter in der richtigen Reihenfolge abgerufen werden. Ich poste das nur, weil ich eine Weile gebraucht habe, um den Originalcode zu verstehen und die Reihenfolge der Befehle zu verdeutlichen. Das volle Guthaben sollte noch an @Xeo gehen. Wenn ich etwas falsch finde mit meiner Implementierung, werde ich zurückkommen und bearbeiten, aber bisher habe ich bei meinen Tests keine Probleme gesehen.

%Vor%

Dies funktioniert auch mit Visual Studio 2013, habe keine früheren Versionen ausprobiert.

    
Lambage 29.01.2014 14:36
quelle