Als ich nachforschte, wie man die C ++ - Bibliothek mit ein wenig C-Kenntnissen verwendet, tauchten häufig Vorlagen auf. Zu diesem Zeitpunkt habe ich die Vorlage nicht gut verstanden und übersprungen, aber als ich sie erneut überprüfte, war sie sehr nützlich. Deshalb habe ich den gesuchten Inhalt mit einem einfachen Beispiel und Beispielen zusammengefasst, die verwendet werden können.
Als ich die Vorlage nachschlug, war ich durch die Namensvorlage verwirrt. Vergessen Sie die Bedeutung der Wortvorlage und lesen Sie sie. Eine Vorlage ist einfach eine typunabhängige Funktion (oder Klasse). In C ++ ist es normal, Typen für Variablen und Rückgabewerte anzugeben, aber es ist nutzlos und unmöglich, Funktionen (oder Klassen) zu erstellen, die für alle Typen geeignet sind, also Funktionen (oder Klassen), die alle Typen mit einer Funktion namens template empfangen ) Kann erstellt werden.
Das Anwenden einer Vorlage ist einfach. Fügen Sie einfach `template <Typname Variablenname>`
über der Funktion (oder Klasse) hinzu, und der Typ des angegebenen Variablennamens in dieser Funktion (oder Klasse) ändert sich in den vom Aufrufer angegebenen Typ. Machen.
Sie können es wie eine normale Funktion aufrufen.
cppMain.cpp
template <Typname Argumentname>
Funktionsname ungültig machen(Argumentname){
Verarbeitung in der Funktion
}
//Wie rufe ich an?
int main(){
int a = 1;
Funktionsname(a);
Funktionsname<int>(a);
}
Wenn Sie den Rückgabetyp anwenden, fügen Sie einfach `template <Typname Variablenname>`
über der Funktion (oder Klasse) hinzu. Eine Sache, bei der Sie vorsichtig sein sollten, ist der Typ, der mit `` `return``` zurückgegeben wird. Da der von return zurückgegebene Typ mit dem definierten Rückgabetyp identisch sein muss, muss der Rückgabewertname im folgenden Beispiel zurückgegeben werden.
cppMain.cpp
template <Typname Gibt den Namen zurück>
Rückgabewert Name Funktionsname(){
Name zurückgeben a=Wert;
Verarbeitung in der Funktion
return a;
}
In diesem Beispiel erstellen wir eine Funktion mit einem Argument T, das jeden Typ akzeptieren kann. Der Inhalt der Funktion zeigt nur den Typ der Variablen T in der Standardausgabe an. Wenn der Funktion der Typ int zugewiesen wird, wird der Typ std :: string angegeben, und das Ergebnis, wenn der Zeiger angegeben wird, wird angezeigt.
cppMain.cpp
#include <typeinfo>
#include <iostream>
#include <cxxabi.h>
template <typename T>
static void print_type(T){
int status;
std::cout << "type name:" << abi::__cxa_demangle(typeid(T).name(), 0, 0, &status) << std::endl;
}
int main(){
int a = 1;
print_type(a);
std::string b = "ab";
print_type(b);
char* e = "ab";
print_type(e);
}
Ergebnis
# ./cppMain
type name:int
type name:std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> >
type name:char*
Wenn wir uns die Ergebnisse ansehen, können wir sehen, dass wir alle Standardtypen wie int, Klassen wie std :: string und Zeiger übergeben können. Dieses Mal ist es eine Funktion, die nur standardmäßig ausgegeben wird, daher weiß ich nicht, wie nützlich sie ist, aber ich werde ein Beispiel vorstellen, das im nächsten Beispiel tatsächlich verwendet werden kann.
Als Beispiel, das tatsächlich verwendet werden kann, nehmen Sie den Konverter von Einstellen des C ++ - und Python-Konverters mit Boost-Python.
Im vorherigen Beispiel war es ein Konverter, der auf den Typ int beschränkt war. Durch Anwenden einer Vorlage ist es jetzt möglich, andere als den Typ int zu konvertieren. Ich habe auch eine Vorlage auf die Funktion `` get_list ()
`angewendet, um die Liste abzurufen, sodass sie für dieselbe Funktion einen anderen Rückgabewert zurückgibt.
Dies macht es unnötig, Konverter für alle Typen zu erstellen. Wenn es Funktionen gibt, die gemeinsam verwendet werden können, kann dies durch einfaches Ändern des Offenlegungsports in Python erfolgen.
Nach der Anwendung
cppMod.cpp
#include <boost/python.hpp>
#include <iostream>
template <typename T>
struct vec_to_list_convert {
static PyObject* convert(std::vector<T> const& vec) {
boost::python::list pyList;
for (auto item: vec) {
pyList.append(item);
}
return boost::python::incref(pyList.ptr());
}
};
class Greeting {
public:
template <typename T>
std::vector<T> get_list() {
std::vector<T> cppVec;
cppVec.push_back(1);
cppVec.push_back(2);
return cppVec;
}
};
BOOST_PYTHON_MODULE(CppMod) {
boost::python::to_python_converter<const std::vector<int>, vec_to_list_convert<int>>();
boost::python::to_python_converter<const std::vector<double>, vec_to_list_convert<double>>();
boost::python::class_<Greeting>("greeting")
.def("get_int_list", &Greeting::get_list<int>)
.def("get_double_list", &Greeting::get_list<double>);
}
Ergebnis
# python3
>>> import CppMod
>>> a=CppMod.greeting()
>>> a.get_int_list()
[1, 2]
>>> a.get_double_list()
[1.0, 2.0]
Ich habe eine Vorlage zusammengestellt. Obwohl es kenntnisreich genug ist, um sich zu entwickeln, ohne es zu wissen, war es sehr nützlich, um die Verwendung der Bibliothek zu untersuchen und eine effiziente und saubere codebewusste Entwicklung zu realisieren.
Recommended Posts