Thread benutzen wie



  • Wie syncronisier ich die threads. Ich hab ein Programm geschrieben bei demm es einen Knopf und ein Textfeld giebt. Beim Drücken auf dem Knopf wird ein Thread gestartet in dem eine Schleife läuf die überprüft ob z=1 ist. Sie läuft solange bis z=0 ist. Auserdem wird beim Knopfdruck z auf 1 gesetzt. Der Thread schreibt mit hilfe0 von Delegate aa ins Textfeld. Wenn man ein weiteresmal auf dem Knopf drückt wird z auf 0 gesetzt. Und somit Die schlleife im Thread beended. Wodurch der Thread auch beendet wird. Das Programm läuft ohne Fehler. Muss ich da noch irgendwas syncronisieren wenn ja wie?

    Hier das Programm

    #include<Windows.h> 
    int c=0;
    int z=1;
    #pragma once 
    
    namespace Thread1 { 
    
        using namespace System; 
        using namespace System::ComponentModel; 
        using namespace System::Collections; 
        using namespace System::Windows::Forms; 
        using namespace System::Data; 
        using namespace System::Drawing; 
    
        /// <summary> 
        /// Zusammenfassung für Form1 
        /// </summary> 
        public ref class Form1 : public System::Windows::Forms::Form 
        { 
        public: 
            Form1(void) 
            { 
                InitializeComponent(); 
                // 
                //TODO: Konstruktorcode hier hinzufügen. 
                // 
            } 
    
        protected: 
            /// <summary> 
            /// Verwendete Ressourcen bereinigen. 
            /// </summary> 
            ~Form1() 
            { 
                if (components) 
                { 
                    delete components; 
                } 
            } 
        private: System::Windows::Forms::Button^  button1; 
        static System::Windows::Forms::TextBox^  s; 
        protected: 
    
        public: 
            /// <summary> 
            /// Erforderliche Designervariable. 
            /// </summary> 
            System::ComponentModel::Container ^components; 
    
    #pragma region Windows Form Designer generated code 
            /// <summary> 
            /// Erforderliche Methode für die Designerunterstützung. 
            /// Der Inhalt der Methode darf nicht mit dem Code-Editor geändert werden. 
            /// </summary> 
            void InitializeComponent(void) 
            { 
                this->button1 = (gcnew System::Windows::Forms::Button()); 
                this->s = (gcnew System::Windows::Forms::TextBox()); 
                this->SuspendLayout(); 
                // 
                // button1 
                // 
                this->button1->Location = System::Drawing::Point(13, 26); 
                this->button1->Name = L"button1"; 
                this->button1->Size = System::Drawing::Size(75, 23); 
                this->button1->TabIndex = 0; 
                this->button1->Text = L"button1"; 
                this->button1->UseVisualStyleBackColor = true; 
                this->button1->Click += gcnew System::EventHandler(this, &Form1::t); 
                // 
                // s 
                // 
                this->s->Location = System::Drawing::Point(35, 98); 
                this->s->Name = L"s"; 
                this->s->Size = System::Drawing::Size(100, 20); 
                this->s->TabIndex = 1; 
                // 
                // Form1 
                // 
                this->AutoScaleDimensions = System::Drawing::SizeF(6, 13); 
                this->AutoScaleMode = System::Windows::Forms::AutoScaleMode::Font; 
                this->ClientSize = System::Drawing::Size(292, 266); 
                this->Controls->Add(this->s); 
                this->Controls->Add(this->button1); 
                this->Name = L"Form1"; 
                this->Text = L"Form1"; 
                this->ResumeLayout(false); 
                this->PerformLayout(); 
    
            } 
    
    #pragma endregion 
        delegate void Delg_1(int zahl_1); 
        Threading::Thread^ newThread;
    
          static void update_1(int zahl_1) 
            { 
    
                    if(Thread1::Form1::s->InvokeRequired) 
                    { 
                        Thread1::Form1::Delg_1^a=gcnew Delg_1(update_1); 
                         Thread1::Form1::s->Invoke(a,1); 
                    } 
                    else 
                    { 
                       Thread1::Form1::s->Text = "aa"; 
                    } 
    
            } 
    
       void PR () 
            { 
    
    				while(z)
    				{
                   Thread1::Form1::Delg_1^a=gcnew Delg_1(update_1); 
                         Thread1::Form1::s->Invoke(a,1); 
    				}   
    
            } 
        private: System::Void t(System::Object^  sender, System::EventArgs^  e) { 
                     HANDLE    tr;   
    
                     DWORD    N;   
    				  c=c+1;
    				  if(c>1)
    				  {
    					  c=0;
    
    				  }
    				  if(c==1)
    				  {
                        z=1;
                     newThread = gcnew 
                    Threading::Thread(gcnew Threading::ThreadStart(this,&Thread1::Form1::PR)); 
                     newThread->Start(); 
    				  }
    				  else
    				  {
    
    					  z=0;
    
    				  }
    
    ; 
    
                 } 
        }; 
    }
    


  • Hallo Hört mich jemand wie synchronisiere ich den zugriff auf die selben Variablen?



  • Jim20115 schrieb:

    Hallo Hört mich jemand wie synchronisiere ich den zugriff auf die selben Variablen?

    Es gibt drei Wege:
    a.) Du marschallst mit Control.Invoke(..) alle Aufrufe auf denselben Thread
    b.) Du benutzt Locking (mit System::Threading::Monitor o.ä.)
    c.) Du benutzt Events (mit System::Threading::ManualResetEvent / AutoResetEvent o.ä.)



  • Gibt es die möglichkeit, dass wenn ich eine Variable in einem Thread lesen bezihungsweise beschreiben möchte. Dass ich diese dann für die anderen Threads sperren lass und erst dann wieder freigeb wenn der lese bezihungswise schreibvorgang beendet ist. Wenn ein Thread versucht auf eine gesperte Variable zuzugreifen soll er warten bis sie freigegeben ist und erst dann weitermachen. Ist das möglich? und wie geht dass?



  • Jim20115 schrieb:

    Gibt es die möglichkeit, dass wenn ich eine Variable in einem Thread lesen bezihungsweise beschreiben möchte. Dass ich diese dann für die anderen Threads sperren lass und erst dann wieder freigeb wenn der lese bezihungswise schreibvorgang beendet ist. Wenn ein Thread versucht auf eine gesperte Variable zuzugreifen soll er warten bis sie freigegeben ist und erst dann weitermachen. Ist das möglich? und wie geht dass?

    Nennt sich Locking und lässt sich mit der oben beschriebenen Klasse realisieren.



  • Ich hab folgendes ausprobirt

    #include<Windows.h> 
    #include<Windows.h> 
    int c=0;
    int z=1;
    #pragma once 
    
    namespace Thread1 { 
    
        using namespace System; 
        using namespace System::ComponentModel; 
        using namespace System::Collections; 
        using namespace System::Windows::Forms; 
        using namespace System::Data; 
        using namespace System::Drawing; 
    
        /// <summary> 
        /// Zusammenfassung für Form1 
        /// </summary> 
        public ref class Form1 : public System::Windows::Forms::Form 
        { 
        public: 
            Form1(void) 
            { 
                InitializeComponent(); 
                // 
                //TODO: Konstruktorcode hier hinzufügen. 
                // 
            } 
    
        protected: 
            /// <summary> 
            /// Verwendete Ressourcen bereinigen. 
            /// </summary> 
            ~Form1() 
            { 
                if (components) 
                { 
                    delete components; 
                } 
            } 
        private: System::Windows::Forms::Button^  button1; 
        static System::Windows::Forms::TextBox^  s; 
        protected: 
    
        public: 
            /// <summary> 
            /// Erforderliche Designervariable. 
            /// </summary> 
            System::ComponentModel::Container ^components; 
    
    #pragma region Windows Form Designer generated code 
            /// <summary> 
            /// Erforderliche Methode für die Designerunterstützung. 
            /// Der Inhalt der Methode darf nicht mit dem Code-Editor geändert werden. 
            /// </summary> 
            void InitializeComponent(void) 
            { 
                this->button1 = (gcnew System::Windows::Forms::Button()); 
                this->s = (gcnew System::Windows::Forms::TextBox()); 
                this->SuspendLayout(); 
                // 
                // button1 
                // 
                this->button1->Location = System::Drawing::Point(13, 26); 
                this->button1->Name = L"button1"; 
                this->button1->Size = System::Drawing::Size(75, 23); 
                this->button1->TabIndex = 0; 
                this->button1->Text = L"button1"; 
                this->button1->UseVisualStyleBackColor = true; 
                this->button1->Click += gcnew System::EventHandler(this, &Form1::t); 
                // 
                // s 
                // 
                this->s->Location = System::Drawing::Point(35, 98); 
                this->s->Name = L"s"; 
                this->s->Size = System::Drawing::Size(100, 20); 
                this->s->TabIndex = 1; 
                // 
                // Form1 
                // 
                this->AutoScaleDimensions = System::Drawing::SizeF(6, 13); 
                this->AutoScaleMode = System::Windows::Forms::AutoScaleMode::Font; 
                this->ClientSize = System::Drawing::Size(292, 266); 
                this->Controls->Add(this->s); 
                this->Controls->Add(this->button1); 
                this->Name = L"Form1"; 
                this->Text = L"Form1"; 
                this->ResumeLayout(false); 
                this->PerformLayout(); 
    
            } 
    
    #pragma endregion 
        delegate void Delg_1(int zahl_1); 
        Threading::Thread^ newThread;
    
          static void update_1(int zahl_1) 
            { 
    
                    if(Thread1::Form1::s->InvokeRequired) 
                    { 
                        Thread1::Form1::Delg_1^a=gcnew Delg_1(update_1); 
                         Thread1::Form1::s->Invoke(a,1); 
                    } 
                    else 
                    { 
                       Thread1::Form1::s->Text = "aa"; 
                    } 
    
            } 
    
       void PR () 
            { 
    			    int h=1;
    				while(h)
    				{
    
    				  Threading::Monitor::TryEnter(z);
    					  h=z;
    					  Threading::Monitor::Exit(z);
                   Thread1::Form1::Delg_1^a=gcnew Delg_1(update_1); 
                         Thread1::Form1::s->Invoke(a,1); 
    				}   
    
            } 
        private: System::Void t(System::Object^  sender, System::EventArgs^  e) { 
                     HANDLE    tr;   
    
                     DWORD    N;   
    				  c=c+1;
    				  if(c>1)
    				  {
    					  c=0;
    
    				  }
    				  if(c==1)
    				  {
                          Threading::Monitor::TryEnter(z);
    					  z=1;
    					  Threading::Monitor::Exit(z);
                     newThread = gcnew 
                     Threading::Thread(gcnew Threading::ThreadStart(this,&Thread1::Form1::PR)); 
                     newThread->Start(); 
    				  }
    				  else
    				  {
    
    					   Threading::Monitor::TryEnter(z);
    					  z=0;
    					  Threading::Monitor::Exit(z);
    
    				  }
    
    ; 
    
                 } 
        }; 
    }
    

    und bekomme folgende fehlermeldung wenn ich den Knopf drück. Woran liegt dass?

    "Thread.exe" (Verwaltet (v4.0.30319)): "C:\WINDOWS\Microsoft.Net\assembly\GAC_32\mscorlib\v4.0_4.0.0.0__b77a5c561934e089\mscorlib.dll" geladen
    "Thread.exe" (Verwaltet (v4.0.30319)): "C:\Thread\Funktion in Funktion\Release\Thread.exe" geladen, Symbole geladen.
    "Thread.exe" (Verwaltet (v4.0.30319)): "C:\WINDOWS\Microsoft.Net\assembly\GAC_MSIL\System.Windows.Forms\v4.0_4.0.0.0__b77a5c561934e089\System.Windows.Forms.dll" geladen
    "Thread.exe" (Verwaltet (v4.0.30319)): "C:\WINDOWS\Microsoft.Net\assembly\GAC_MSIL\System.Drawing\v4.0_4.0.0.0__b03f5f7f11d50a3a\System.Drawing.dll" geladen
    "Thread.exe" (Verwaltet (v4.0.30319)): "C:\WINDOWS\Microsoft.Net\assembly\GAC_MSIL\System\v4.0_4.0.0.0__b77a5c561934e089\System.dll" geladen
    "Thread.exe" (Verwaltet (v4.0.30319)): "C:\WINDOWS\Microsoft.Net\assembly\GAC_MSIL\mscorlib.resources\v4.0_4.0.0.0_de_b77a5c561934e089\mscorlib.resources.dll" geladen
    Eine Ausnahme (erste Chance) des Typs "System.Threading.SynchronizationLockException" ist in Thread.exe aufgetreten.
    Eine nicht behandelte Ausnahme des Typs "System.Threading.SynchronizationLockException" ist in Thread.exe aufgetreten.
    
    Zusätzliche Informationen: Die Objektsynchronisationsmethode wurde von einem nicht synchronisierten Codeblock aufgerufen.
    
    Das Programm "[4036] Thread.exe: Verwaltet (v4.0.30319)" wurde mit Code 0 (0x0) beendet.
    


  • Benutze keine globalen Variabeln!
    Ich sag Dir: Nimm C#, da hättest Du jetzt keine Verwirrung, es ist einfacher und sinnvoller.

    Ich kann Dir nicht mehr weiterhelfen, der Unterschied wie es ist und wie es sein sollte ist einfach zu gross.

    Nimm C#!
    (Oder meinetwegen C++, aber nicht C++/CLI.)



  • Was passiert wenn ich mehrere Threads habe, in folgenden Fällen:
    Fall 1) alle Threads lesen gleichzeitig die selbe Variable.
    Fall 2) alle Threads beschreiben gleichzeitig die selbe Variable.
    Fall 3) einige beschreiben andere lesen die selbe Variable.
    Gibt es in der Windows api eigentlich funktionen womit ich den zugriff auf dieselben Variablen synchronisiren kann. Diese Funktionen könnte ich doch auch in meinem Programm verwenden oder?



  • Fall 1 ist harmlos, Fall 2 und 3 könnten Probleme machen (und sind im Allgemeinen undefiniert).

    Unter der WinAPI kenne ich Synchronisationsobjekte wie CriticalSection oder Mutex, die ich verwenden würde, aber da du sowieso im .NET-Umfeld agierst, bist du mit den .NET-Klassen wie System.Threading.Mutex vermutlich besser aufgehoben.



  • @Jim20115
    Kann mich der Meinung nur anschließen, .NET-Oberfläche macht mit C++/CLI keinen Sinn. C# ist da ein muß. Ich persönlich kann für "echtes" C++, Qt empfehlen. Wir entwickeln seit Jahren ,im größeren Team, damit zielgerichtet, effiziente Software.



  • Heißt das in Fall 1 giebt es keine Probleme. Ich habs jetzt so gelöst das ich einen Text zum Thread hinschike. Wenn der dort ankommt beende ich den Thread.
    Ich kann mit
    Thread->Name="a" einen Text zum Thread schiken und mit Threading::Thread::CurrentThread->Name im Thread empfangen. Kann ich neben Name auch noch andere Verbindungen zum Thread erschafen.
    zum Beispiel
    im Hauptprogramm
    Thread->a="1"
    Thread->b="22"
    Thread->c="11"
    im Thread
    printf(Threading::Thread::CurrentThread->a)
    printf(Threading::Thread::CurrentThread->b)
    printf(Threading::Thread::CurrentThread->c)
    versteht ihr was ich meine. Ist es möglich von mehreren Threads aus gleichzeitig verschiedene Nachrichten an den Thread zu schiecken.
    Wan steht eigentlich dann in Threading::Thread::CurrentThread->Name drin. Wenn ich zum beispiel 3 threads habe. An thread 1 schickt Thread 2 "2" hin und Thread 3 schickt "3" zu thread 1.
    Und ich ruf in thread 1 Threading::Thread::CurrentThread->Name zweimal auf. Dann wird entweder beim ersten aufruf "2" zurückgelifert und beim zweiten "3" oder umgekehrt ist das so richtig wie ich das denke?



  • OT: Das ist nicht zu fassen...



  • Hallo Jim20115,

    hast du auch nur im Ansatz verstanden, was dir seit 4 Seiten versucht wird zu sagen? Bist du sicher, dass du für Threading bereit bist? Wenn ja, wieso nimmst du dann nicht endlich mal an, was dir an Tipps gegeben wird?

    Zum Thema: Wenn du Daten an einen Thread geben willst, nutze eine Queue.
    Erstelle eine Klasse, die die zu übergebenden Properties beinhaltet. Schreibe die Daten in die Queue und lese die Daten mit deinem Thread aus.

    Vergiss allerdings nicht, beim Beschreiben / Lesen der Queue die Zugriffe zu synchronisieren.



  • Ich versteh leider nicht wie ich denn zugriff synchronisiere könnt ich vieleicht eine erklärung kriegen wie das geht? Ich hab nur herausgefunden wie ich Strings an Threads schiecken kann das sieht dann so aus.

    #include<Windows.h> 
    
    int c=0;
    
    #pragma once 
    
    namespace Thread1 { 
    
        using namespace System; 
        using namespace System::ComponentModel; 
        using namespace System::Collections; 
        using namespace System::Windows::Forms; 
        using namespace System::Data; 
        using namespace System::Drawing; 
    
        /// <summary> 
        /// Zusammenfassung für Form1 
        /// </summary> 
        public ref class Form1 : public System::Windows::Forms::Form 
        { 
        public: 
            Form1(void) 
            { 
                InitializeComponent(); 
                // 
                //TODO: Konstruktorcode hier hinzufügen. 
                // 
            } 
    
        protected: 
            /// <summary> 
            /// Verwendete Ressourcen bereinigen. 
            /// </summary> 
            ~Form1() 
            { 
                if (components) 
                { 
                    delete components; 
                } 
            } 
        private: System::Windows::Forms::Button^  button1; 
        static System::Windows::Forms::TextBox^  s; 
        protected: 
    
        public: 
            /// <summary> 
            /// Erforderliche Designervariable. 
            /// </summary> 
            System::ComponentModel::Container ^components; 
    
    #pragma region Windows Form Designer generated code 
            /// <summary> 
            /// Erforderliche Methode für die Designerunterstützung. 
            /// Der Inhalt der Methode darf nicht mit dem Code-Editor geändert werden. 
            /// </summary> 
            void InitializeComponent(void) 
            { 
                this->button1 = (gcnew System::Windows::Forms::Button()); 
                this->s = (gcnew System::Windows::Forms::TextBox()); 
                this->SuspendLayout(); 
                // 
                // button1 
                // 
                this->button1->Location = System::Drawing::Point(13, 26); 
                this->button1->Name = L"button1"; 
                this->button1->Size = System::Drawing::Size(75, 23); 
                this->button1->TabIndex = 0; 
                this->button1->Text = L"button1"; 
                this->button1->UseVisualStyleBackColor = true; 
                this->button1->Click += gcnew System::EventHandler(this, &Form1::t); 
                // 
                // s 
                // 
                this->s->Location = System::Drawing::Point(35, 98); 
                this->s->Name = L"s"; 
                this->s->Size = System::Drawing::Size(100, 20); 
                this->s->TabIndex = 1; 
                // 
                // Form1 
                // 
                this->AutoScaleDimensions = System::Drawing::SizeF(6, 13); 
                this->AutoScaleMode = System::Windows::Forms::AutoScaleMode::Font; 
                this->ClientSize = System::Drawing::Size(292, 266); 
                this->Controls->Add(this->s); 
                this->Controls->Add(this->button1); 
                this->Name = L"Form1"; 
                this->Text = L"Form1"; 
                this->ResumeLayout(false); 
                this->PerformLayout(); 
    
            } 
    
    #pragma endregion 
        delegate void Delg_1(int zahl_1); 
        Threading::Thread^ newThread;
    
          static void update_1(int zahl_1) 
            { 
    
                    if(Thread1::Form1::s->InvokeRequired) 
                    { 
                        Thread1::Form1::Delg_1^a=gcnew Delg_1(update_1); 
                         Thread1::Form1::s->Invoke(a,1); 
                    } 
                    else 
                    { 
                       Thread1::Form1::s->Text = "aa"; 
                    } 
    
            } 
    
       void PR () 
            { 
    			    int h=1;
    				while(h)
    				{
    
    					if(Threading::Thread::CurrentThread->Name=="1")
    					{
    						h=0;
    					}
    
                   Thread1::Form1::Delg_1^a=gcnew Delg_1(update_1); 
                         Thread1::Form1::s->Invoke(a,1); 
    				}   
    
            } 
       static int u=0;
        private: System::Void t(System::Object^  sender, System::EventArgs^  e) { 
                     HANDLE    tr;   
    
                     DWORD    N;   
    				  c=c+1;
    				  if(c>1)
    				  {
    					  c=0;
    
    				  }
    				  if(c==1)
    				  {
    					  newThread = gcnew 
                     Threading::Thread(gcnew Threading::ThreadStart(this,&Thread1::Form1::PR)); 
    
    				 newThread->Start(); 
    
    				  }
    				  else
    				  { 
    
    					newThread->Name="1";
    
    				  }
    
    ; 
    
                 } 
        }; 
    }
    


  • Wie wäre es denn mit ein wenig eigeninitiative?

    Dieses fucking Tutorial arbeitest du bitte durch!



  • Ich kann leider kein Englisch.
    kennt sich vieleicht jemand mit der Materie aus und könnte folgenden Cod berichtigen

    #include<Windows.h> 
    
    int c=0; 
    int z=1; 
    #pragma once 
    
    namespace Thread1 { 
    
        using namespace System; 
        using namespace System::ComponentModel; 
        using namespace System::Collections; 
        using namespace System::Windows::Forms; 
        using namespace System::Data; 
        using namespace System::Drawing; 
    
        /// <summary> 
        /// Zusammenfassung für Form1 
        /// </summary> 
        public ref class Form1 : public System::Windows::Forms::Form 
        { 
        public: 
            Form1(void) 
            { 
                InitializeComponent(); 
                // 
                //TODO: Konstruktorcode hier hinzufügen. 
                // 
            } 
    
        protected: 
            /// <summary> 
            /// Verwendete Ressourcen bereinigen. 
            /// </summary> 
            ~Form1() 
            { 
                if (components) 
                { 
                    delete components; 
                } 
            } 
        private: System::Windows::Forms::Button^  button1; 
        static System::Windows::Forms::TextBox^  s; 
        protected: 
    
        public: 
            /// <summary> 
            /// Erforderliche Designervariable. 
            /// </summary> 
            System::ComponentModel::Container ^components; 
    
    #pragma region Windows Form Designer generated code 
            /// <summary> 
            /// Erforderliche Methode für die Designerunterstützung. 
            /// Der Inhalt der Methode darf nicht mit dem Code-Editor geändert werden. 
            /// </summary> 
            void InitializeComponent(void) 
            { 
                this->button1 = (gcnew System::Windows::Forms::Button()); 
                this->s = (gcnew System::Windows::Forms::TextBox()); 
                this->SuspendLayout(); 
                // 
                // button1 
                // 
                this->button1->Location = System::Drawing::Point(13, 26); 
                this->button1->Name = L"button1"; 
                this->button1->Size = System::Drawing::Size(75, 23); 
                this->button1->TabIndex = 0; 
                this->button1->Text = L"button1"; 
                this->button1->UseVisualStyleBackColor = true; 
                this->button1->Click += gcnew System::EventHandler(this, &Form1::t); 
                // 
                // s 
                // 
                this->s->Location = System::Drawing::Point(35, 98); 
                this->s->Name = L"s"; 
                this->s->Size = System::Drawing::Size(100, 20); 
                this->s->TabIndex = 1; 
                // 
                // Form1 
                // 
                this->AutoScaleDimensions = System::Drawing::SizeF(6, 13); 
                this->AutoScaleMode = System::Windows::Forms::AutoScaleMode::Font; 
                this->ClientSize = System::Drawing::Size(292, 266); 
                this->Controls->Add(this->s); 
                this->Controls->Add(this->button1); 
                this->Name = L"Form1"; 
                this->Text = L"Form1"; 
                this->ResumeLayout(false); 
                this->PerformLayout(); 
    
            } 
    
    #pragma endregion 
        delegate void Delg_1(int zahl_1); 
        Threading::Thread^ newThread; 
    
          static void update_1(int zahl_1) 
            { 
    
                    if(Thread1::Form1::s->InvokeRequired) 
                    { 
                        Thread1::Form1::Delg_1^a=gcnew Delg_1(update_1); 
                         Thread1::Form1::s->Invoke(a,1); 
                    } 
                    else 
                    { 
                       Thread1::Form1::s->Text = "aa"; 
                    } 
    
            } 
    
       void PR () 
            { 
                    int h=1; 
                    while(h) 
                    { 
    
                      Threading::Monitor::TryEnter(z); 
                          h=z; 
                          Threading::Monitor::Exit(z); 
                   Thread1::Form1::Delg_1^a=gcnew Delg_1(update_1); 
                         Thread1::Form1::s->Invoke(a,1); 
                    }   
    
            } 
        private: System::Void t(System::Object^  sender, System::EventArgs^  e) { 
                     HANDLE    tr;   
    
                     DWORD    N;   
                      c=c+1; 
                      if(c>1) 
                      { 
                          c=0; 
    
                      } 
                      if(c==1) 
                      { 
                          Threading::Monitor::TryEnter(z); 
                          z=1; 
                          Threading::Monitor::Exit(z); 
                     newThread = gcnew 
                     Threading::Thread(gcnew Threading::ThreadStart(this,&Thread1::Form1::PR)); 
                     newThread->Start(); 
                      } 
                      else 
                      { 
    
                           Threading::Monitor::TryEnter(z); 
                          z=0; 
                          Threading::Monitor::Exit(z); 
    
                      } 
    
    ; 
    
                 } 
        }; 
    }
    

    ich bekomme folgende Fehlermeldung

    "Thread.exe" (Verwaltet (v4.0.30319)): "C:\WINDOWS\Microsoft.Net\assembly\GAC_32\mscorlib\v4.0_4.0.0.0__b77a5c561934e089\mscorlib.dll" geladen 
    "Thread.exe" (Verwaltet (v4.0.30319)): "C:\Thread\Funktion in Funktion\Release\Thread.exe" geladen, Symbole geladen. 
    "Thread.exe" (Verwaltet (v4.0.30319)): "C:\WINDOWS\Microsoft.Net\assembly\GAC_MSIL\System.Windows.Forms\v4.0_4.0.0.0__b77a5c561934e089\System.Windows.Forms.dll" geladen 
    "Thread.exe" (Verwaltet (v4.0.30319)): "C:\WINDOWS\Microsoft.Net\assembly\GAC_MSIL\System.Drawing\v4.0_4.0.0.0__b03f5f7f11d50a3a\System.Drawing.dll" geladen 
    "Thread.exe" (Verwaltet (v4.0.30319)): "C:\WINDOWS\Microsoft.Net\assembly\GAC_MSIL\System\v4.0_4.0.0.0__b77a5c561934e089\System.dll" geladen 
    "Thread.exe" (Verwaltet (v4.0.30319)): "C:\WINDOWS\Microsoft.Net\assembly\GAC_MSIL\mscorlib.resources\v4.0_4.0.0.0_de_b77a5c561934e089\mscorlib.resources.dll" geladen 
    Eine Ausnahme (erste Chance) des Typs "System.Threading.SynchronizationLockException" ist in Thread.exe aufgetreten. 
    Eine nicht behandelte Ausnahme des Typs "System.Threading.SynchronizationLockException" ist in Thread.exe aufgetreten. 
    
    Zusätzliche Informationen: Die Objektsynchronisationsmethode wurde von einem nicht synchronisierten Codeblock aufgerufen. 
    
    Das Programm "[4036] Thread.exe: Verwaltet (v4.0.30319)" wurde mit Code 0 (0x0) beendet.
    

    Was bedeutet Die Objektsynchronisationsmethode wurde von einem nicht synchronisierten Codeblock aufgerufen.
    Heist das ich darf
    Threading::Monitor::TryEnter(z);
    und Threading::Monitor::Exit(z);
    nur zwichen zwei bestimmten befehlen verwenden die angeben das der Codblock synchronisiert ist oder muss ich bei den Projecteinstellungen angeben das ich einen synchronisierten Cod verwenden möchte?



  • Was bedeutet Die Objektsynchronisationsmethode wurde von einem nicht synchronisierten Codeblock aufgerufen.

    ➡
    http://msdn.microsoft.com/de-de/library/system.threading.synchronizationlockexception(v=vs.80).aspx

    Heist das ich darf
    Threading::Monitor::TryEnter(z);
    und Threading::Monitor::Exit(z);
    nur zwichen zwei bestimmten befehlen verwenden die angeben das der Codblock synchronisiert ist oder muss ich bei den Projecteinstellungen angeben das ich einen synchronisierten Cod verwenden möchte?

    Nein und Nein.

    Es bedeutet: Rufe nicht Exit(..) auf, wenn nicht gelockt ist!
    Monitor::TryEnter(..) hat einen Rückgabe Wert -> Prüfe den!
    Lies das: http://msdn.microsoft.com/de-de/library/system.threading.monitor(v=vs.80).aspx

    Ich denke, es ist besser die Mutex Klasse zu verwenden, aber noch besser wäre C# zu verwenden und Englisch zu lernen. Aber hey, die MSDN Doku ist auch Deutsch!



  • ich hab gelesen dass wenn der aktuelle Thread gesperrt ist lievert TryEnter eine 1. Dass heisst wenn es nicht 1 ist hat es die erlaubnis. Dann müsste folgendes Funktionieren.

    #include<Windows.h> 
    
    int c=0; 
    int z=1; 
    int sch=1;
    #pragma once 
    
    namespace Thread1 { 
    
        using namespace System; 
        using namespace System::ComponentModel; 
        using namespace System::Collections; 
        using namespace System::Windows::Forms; 
        using namespace System::Data; 
        using namespace System::Drawing; 
    
        /// <summary> 
        /// Zusammenfassung für Form1 
        /// </summary> 
        public ref class Form1 : public System::Windows::Forms::Form 
        { 
        public: 
            Form1(void) 
            { 
                InitializeComponent(); 
                // 
                //TODO: Konstruktorcode hier hinzufügen. 
                // 
            } 
    
        protected: 
            /// <summary> 
            /// Verwendete Ressourcen bereinigen. 
            /// </summary> 
            ~Form1() 
            { 
                if (components) 
                { 
                    delete components; 
                } 
            } 
        private: System::Windows::Forms::Button^  button1; 
        static System::Windows::Forms::TextBox^  s; 
        protected: 
    
        public: 
            /// <summary> 
            /// Erforderliche Designervariable. 
            /// </summary> 
            System::ComponentModel::Container ^components; 
    
    #pragma region Windows Form Designer generated code 
            /// <summary> 
            /// Erforderliche Methode für die Designerunterstützung. 
            /// Der Inhalt der Methode darf nicht mit dem Code-Editor geändert werden. 
            /// </summary> 
            void InitializeComponent(void) 
            { 
                this->button1 = (gcnew System::Windows::Forms::Button()); 
                this->s = (gcnew System::Windows::Forms::TextBox()); 
                this->SuspendLayout(); 
                // 
                // button1 
                // 
                this->button1->Location = System::Drawing::Point(13, 26); 
                this->button1->Name = L"button1"; 
                this->button1->Size = System::Drawing::Size(75, 23); 
                this->button1->TabIndex = 0; 
                this->button1->Text = L"button1"; 
                this->button1->UseVisualStyleBackColor = true; 
                this->button1->Click += gcnew System::EventHandler(this, &Form1::t); 
                // 
                // s 
                // 
                this->s->Location = System::Drawing::Point(35, 98); 
                this->s->Name = L"s"; 
                this->s->Size = System::Drawing::Size(100, 20); 
                this->s->TabIndex = 1; 
                // 
                // Form1 
                // 
                this->AutoScaleDimensions = System::Drawing::SizeF(6, 13); 
                this->AutoScaleMode = System::Windows::Forms::AutoScaleMode::Font; 
                this->ClientSize = System::Drawing::Size(292, 266); 
                this->Controls->Add(this->s); 
                this->Controls->Add(this->button1); 
                this->Name = L"Form1"; 
                this->Text = L"Form1"; 
                this->ResumeLayout(false); 
                this->PerformLayout(); 
    
            } 
    
    #pragma endregion 
        delegate void Delg_1(int zahl_1); 
        Threading::Thread^ newThread; 
    
          static void update_1(int zahl_1) 
            { 
    
                    if(Thread1::Form1::s->InvokeRequired) 
                    { 
                        Thread1::Form1::Delg_1^a=gcnew Delg_1(update_1); 
                         Thread1::Form1::s->Invoke(a,1); 
                    } 
                    else 
                    { 
                       Thread1::Form1::s->Text = "aa"; 
                    } 
    
            } 
    
       void PR () 
            { 
                    int h=1; 
                    while(h) 
                    { 
    
                       if(Threading::Monitor::TryEnter(z)!=1)
    				   {
                          h=z; 
                          Threading::Monitor::Exit(z); 
    				   }
                   Thread1::Form1::Delg_1^a=gcnew Delg_1(update_1); 
                         Thread1::Form1::s->Invoke(a,1); 
                    }   
    
            } 
        private: System::Void t(System::Object^  sender, System::EventArgs^  e) { 
                     HANDLE    tr;   
    
                     DWORD    N;   
                      c=c+1; 
                      if(c>1) 
                      { 
                          c=0; 
    
                      } 
                      if(c==1) 
                      { 
                             sch=1;
    					  while(sch)
    					  {
                           if(Threading::Monitor::TryEnter(z)!=1)
    					   {
    
                          z=1; 
    					  sch=0;
                          Threading::Monitor::Exit(z); 
    					   }
    					  }
                     newThread = gcnew 
                     Threading::Thread(gcnew Threading::ThreadStart(this,&Thread1::Form1::PR)); 
                     newThread->Start(); 
                      } 
                      else 
                      { 
                          sch=1;
    					  while(sch)
    					  {
                           if(Threading::Monitor::TryEnter(z)!=1)
    					   {
                          z=0; 
    					  sch=0;
                          Threading::Monitor::Exit(z); 
    					   }
    					  }
    
                      } 
    
    ; 
    
                 } 
        }; 
    }
    

    Aber dass hängt sich auf Wo ist der fehler?



  • Je länger je mehr: Benutze C# oder wenigstens hier einfach die Klasse Mutex!



  • Ich hab ein Beispiel gefunden wo mit Hilfe der Classe Mutex gewartet wurde bis ein String beim Thread ankommt der vorher von einem anderen Thread dort hingeschickt wurde. Wie mach ich dass wen ich mehrere Threads habe und die ihre Nachrichten an einen Thread schicken wie halt ich die nachrichten dann auseinander und kommen die dann auch noch ganz an?


Anmelden zum Antworten