Konstraktor nochmal aufrufen? (boost::thread)
-
Ich frage mich gerade wozu bei der Thread Klasse von der Boost Library ein Konstruktor exitiert, bei dem man keine Funktion übergibt. Es würde Sinn ergeben, wenn man sagt, dass man zuerst die Instanz erstellt und später erst die Funktion für den Thread an eine Funktion der Klasse übergibt. Aber so eine Funtkion kann ich nicht finden. Also müsste ich eigentlich den zweiten Konstruktor nochmal aufrufen. Ich hoffe ihr versteht mein Problem. Hier Beispiel wie ich das meine (pseudo code):
void bla() {} int main() { boost::thread asd(&bla); }Hier ist ja alles in Ordnung. Aber jetzt will ich den Thread in einem anderen Gültigkeits bereich starten:
void bla() {} void blaexe (boost::thread &asd) { // Hier soll der Thread gestartet werden } int main() { boost::thread bla(); // Hier noch nicht blaexe(); // Hier dann sonstiger Kram }Wie kann ich jetzt den Thread starten ohne ihn beim erstellen der Instanz zu übergeben???
Hier der Link: http://boost.org/doc/html/thread.html
mfg.
-
joomoo schrieb:
Ich frage mich gerade wozu bei der Thread Klasse von der Boost Library ein Konstruktor exitiert, bei dem man keine Funktion übergibt.
boost Doku schrieb:
Effects: Constructs a thread object representing the current thread of execution.
-
joomoo schrieb:
Wie kann ich jetzt den Thread starten ohne ihn beim erstellen der Instanz zu übergeben???
Indem Du ihn erst dann anlegst, wenn Du ihn brauchst. Damit nicht vorschnell der Destruktor des Threads aufgerufen wird, packst Du ihn am besten in eine Klasse oder Struct.
void bla() {} struct blaexe { blaexe() : m_thrd( &bla ) // Hier wird der Thread gestartet {} private: boost::thread m_thrd; }; int main() { blaexe einBlaexe; // Hier dann sonstiger Kram }irgendwie so
Gruß
Werner
-
Wofür gibt es den Default-Konstruktor?
-
Ehm, hat doch Bashar gepostet.
-
Indem Du ihn erst dann anlegst, wenn Du ihn brauchst. Damit nicht vorschnell der Destruktor des Threads aufgerufen wird, packst Du ihn am besten in eine Klasse oder Struct.
Also ich meine jetzt eigentlich, dass der Thread in einem anderen Gültigkeitsbereich erstellt wird, als in dem er gebraucht wird. Soll heißen, wenn ich den Thread in der blaexe() Funktion erstelle, wird er ja durch den Dekonstruktor automatisch zerstört und ich kann ihn dann z.B. nicht mehr in der Main benutzen. Er soll dann aber noch weiter laufen. Und wenn ich aus blaexe eine Struktur mache, löst das ja mein Problem noch nicht. Ich könnte die thread Klasse static machen, aber ich glaube das ist nicht die Ideallösung. Kann ich einen Thread wirklich nur über den Konstraktor erstellen? Anscheinend ja, weil wofür der Konstruktor ohne Parameter ist, hab ich jetzt verstanden.
Wie lässt sich das Problem lösen?
mfg.
-
Das Thread-Objekt ist ein Objekt wie jedes andere. Wenn es nicht nach verlassen eines Gültigkeitsbereiches zerstört werden soll, was machen wir da in C++? Genau, wir erzeugen ein Objekt auf dem Heap mit new und schleppen den Pointer solange rum bis wir es nicht mehr brauchen. Ob du das Thread-Objekt jetzt direkt mit new instanzierst oder in einem anderen Objekt kapselst, und ebend dieses dynamisch erzeugst, ist eine Design-Entscheidung.
boost::thread* foo() { return new boost::thread(xyz); }Dann gibts da ja noch die Möglichkeit die Threads in einem Vector zu sammeln und den Vector rumzuschleppen.
thread_vec.push_back(new boost::thread(xyz));Du siehst, Thread-Objekte mußt du wie alle anderen Objekte behandeln.
Insofern ist hier keine Patentlösung präsentierbar. Kannste nämlich auch in einer Factory erzeugen, deine Threads. Mußt du selber entscheiden.
-
Danke Artchi! Darauf bin ich gar nicht gekommen! Okay Problem gelöst.
mfg.
-
Bei der Lösung des Problems bin ich gerade wieder auf das Problem gestoßen! Ich möchte keinen normalen Zeiger nehmen, sondern einen std::auto_ptr Zeiger. Leider muss ich dort wieder über den Konstraktor den entsprechenden Zeiger übergeben. Da hab ich dann erstmal 0 gemacht, weil wenn der Thread gar nicht erstellt würde delete nichts macht.
Aber wie setze ich jetzt den zeiger nachträglich bei auto_ptr?
Ich habe mir das so gedacht:auto_ptrZeiger = new boost::thread(boost::bind(par1, par2, par3, &par4));Allerdings erwartet der operator= ein weiteres auto_ptr Objekt und ein cast bringt hier nichts. Außerdem habe ich wieso gehört, dass sich der operator= von auto_ptr anders als gewöhnlich verhält.
Hat jemand ne Referenz zu auto_ptr? Ich habe auf cppreference.com und bei google schon gesucht, aber da war nur die Grundfunktion über den Konstruktor
mfg.
-
Artchi boost::thread ist aber von noncopyable abgeleitet, da wird das mit std::vector problematisch.
-
joomoo schrieb:
auto_ptrZeiger = new boost::thread(boost::bind(par1, par2, par3, &par4));Allerdings erwartet der operator= ein weiteres auto_ptr Objekt und ein cast bringt hier nichts.
Es würde schon so gehen:
p = auto_ptr<boost::thread>(new boost::thread(boost::bind(par1, par2, par3, &par4)));aber besser ist die reset-Methode:
p.reset(new boost::thread(boost::bind(par1, par2, par3, &par4)));
-
Ah danke! Genau die Funktion hab ich gesucht.
mfg.