Gateway_man Geschrieben 7. September 2011 Teilen Geschrieben 7. September 2011 (bearbeitet) Hi leute, es geht um Threading. Mein Chef hätte gerne eine Klasse wo er Funktionen an Thread übergeben kann die diese dann Ausführen, um den ganzen schmuss nicht immer und immer wieder schreiben zu müssen. Ich habe daraufhin ein Beispiel geschrieben von dem ich eigentlich dachte das es funktioniert. Allerdings ist das Form das die Klasse aufruft solange nicht erreichbar wie der Thread läuft (was ja nicht im Sinne der Sache ist). Hier mal die Klasse: using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Windows.Forms; using System.Threading; namespace m_Thread { public class mThread { private Thread _mthread; private IntPtr invokecontrol = IntPtr.Zero; private CallParameterlessFunction function = null; public event EventHandler<EventArgs> OperationFinished = null; public mThread(IntPtr invokecontrol, CallParameterlessFunction function) { this.invokecontrol = invokecontrol; this.function = function; _mthread = new Thread(new ThreadStart(Execute)); } public void Start() { if (invokecontrol != IntPtr.Zero && function != null) _mthread.Start(); } private void Execute() { Control invoker = Control.FromHandle(invokecontrol); //invoker.Invoke(function); IAsyncResult result = invoker.BeginInvoke(function); while (!result.IsCompleted) { Application.DoEvents(); } invoker.EndInvoke(result); OperationFinished(this, EventArgs.Empty); } public void Abort() { if (_mthread != null && _mthread.IsAlive) _mthread.Abort(); } } public delegate void CallParameterlessFunction(); } Hier der beispielaufruf: using System; using System.Collections.Generic; using System.ComponentModel; using System.Data; using System.Drawing; using System.Linq; using System.Text; using System.Windows.Forms; namespace m_Thread { public partial class Form1 : Form { private mThread thread = null; public Form1() { InitializeComponent(); } private void button1_Click(object sender, EventArgs e) { CallParameterlessFunction functionparameter = new CallParameterlessFunction(ThreadFunction); thread = new mThread(richTextBox1.Handle, functionparameter); thread.OperationFinished += new EventHandler<EventArgs>(ThreadFinished); thread.Start(); } private void ThreadFunction() { for (int i = 0; i <= 100000; i++) { richTextBox1.Text += i.ToString() + Environment.NewLine; } } private void ThreadFinished(object sender, EventArgs e) { MessageBox.Show("Thread fertig"); } private void button2_Click(object sender, EventArgs e) { if (thread != null) thread.Abort(); } } } Sieht einer von euch den Fehler? lg Gateway Edit: Ich stand ein wenig auf der Leitung. Das delegate ist hier das Problem. Der milisekündliche Aufruf blockiert scheinbar den Formeigenen Thread. Hat jemand ne alternative. Also es geht quasi darum einem Thread in einer Dll eine beliebige Funktion zu übergeben. Bearbeitet 7. September 2011 von Gateway_man Zitieren Link zu diesem Kommentar Auf anderen Seiten teilen Mehr Optionen zum Teilen...
lilith2k3 Geschrieben 7. September 2011 Teilen Geschrieben 7. September 2011 Du solltest Dir unbedingt mal Visual Studio Asynchronous Programming ansehen :] Zitieren Link zu diesem Kommentar Auf anderen Seiten teilen Mehr Optionen zum Teilen...
realgun Geschrieben 7. September 2011 Teilen Geschrieben 7. September 2011 Verwendest Du .NET 4? Dann beschäftige Dich am besten mal mit der TPL, die bringt alles mit, was Du brauchst... Zitieren Link zu diesem Kommentar Auf anderen Seiten teilen Mehr Optionen zum Teilen...
Gateway_man Geschrieben 7. September 2011 Autor Teilen Geschrieben 7. September 2011 (bearbeitet) hi, danke für den Tipp aber das mit dem asynchronen invoken war nur ein test und wurde auch bereits verworfen da es nicht notwendig war. Ich überleg mir lieber einen Weg wie ich meinem Chef am besten beibringe das es so nicht funktioniert wie er will. So wie ich das verstanden habe will er eine klasse die eine Funktion beinhaltet welcher er funktionen als parameter übergeben kann damit diese dann in einem thread abgearbeitet werden. (ohne delegates) Eventuell werd ich mich nochmal im reflection namespace umschaun. Trotzdem danke, lg Gateway EDIT: @Realgun: Nein er will alles auf dem Framework 2.5 haben (warum auch immer). Ich dachte das Threadpools bereits seit dem 3.5 implementiert wurden. Bearbeitet 7. September 2011 von Gateway_man Zitieren Link zu diesem Kommentar Auf anderen Seiten teilen Mehr Optionen zum Teilen...
realgun Geschrieben 8. September 2011 Teilen Geschrieben 8. September 2011 TPL hat nicht viel mit ThreadPools zu tun (außer dass diese im Hintergrund verwendet werden.) ThreadPools werden schon seit .NET 1.1 unterstützt. Ohne Delegates / Lambda Ausdrücke wird's natürlich schwer, allerdings glaube ich nicht dass Dir Reflection dabei sinnvoll helfen kann. Du könntest aber eine Klasse bauen, die ein paar Standarddelegates bereitstellt (z.B. MethodInvokerDelegate), die kannst Du ja in Methoden nach außen kapseln. Noch ein Tipp: Application.DoEvents solltest Du besser nicht verwenden Zitieren Link zu diesem Kommentar Auf anderen Seiten teilen Mehr Optionen zum Teilen...
Gateway_man Geschrieben 8. September 2011 Autor Teilen Geschrieben 8. September 2011 ...allerdings glaube ich nicht dass Dir Reflection dabei sinnvoll helfen kann. Würde ansich schon so funktionieren allerdings ist die schreibarbeit enorm. Eben wie beim dynamischen laden einer dll. Ein string für den Modulpfad, ein string für den klassennamen (+ namespace) und ein string für die Funktion. Ja wie gesagt Application.DoEvents hatte ich nur zu Testzwecken drin (Beziehungsweise den ganzen asynchronen Vorgang) um festzustellen ob es daran liegt das ich es synchron invoked habe. Danke für die Tipps. lg Gateway Zitieren Link zu diesem Kommentar Auf anderen Seiten teilen Mehr Optionen zum Teilen...
lilith2k3 Geschrieben 8. September 2011 Teilen Geschrieben 8. September 2011 So wie ich das verstanden habe will er eine klasse die eine Funktion beinhaltet welcher er funktionen als parameter übergeben kann damit diese dann in einem thread abgearbeitet werden. (ohne delegates) Contradictio in adiecto Wenn ich einer Funktion eine Funktion mitgebe, geht das lediglich als delegate, bzw. mittels Func<T>, was ja nur der syntaktische Zucker für delegates ist. Alternativ könnten Objekte übergeben werden, die ein Interface implementierten, e.g. void DoAsync() und die im anderen Thread laufende Methode nimmt derartige Objekte entgegen und führt eben die Methode aus. Nachwievor gilt mein obiger Tip. Zitieren Link zu diesem Kommentar Auf anderen Seiten teilen Mehr Optionen zum Teilen...
SilentDemise Geschrieben 8. September 2011 Teilen Geschrieben 8. September 2011 vor allem ist das Zitat die genaue definition eines Delegates. Zitieren Link zu diesem Kommentar Auf anderen Seiten teilen Mehr Optionen zum Teilen...
Gateway_man Geschrieben 8. September 2011 Autor Teilen Geschrieben 8. September 2011 vor allem ist das Zitat die genaue definition eines Delegates. Jup sind ja nichts anderes als Funktionszeiger. Ich hab versucht ihm das verständlich zu machen, aber er meint er will keine delegates (zuviel schreibarbeit). Er sucht am besten eine einzeilige Lösung xD. @lilith2k3: Das mit dem ctp sieht recht interssant aus (auch wenn die syntax n bisschen obskur aussieht). Allerdings nutzen wir noch vs 2008 (nur ein Kollege arbeitet mit vs2010 und das eigentlich nur da er für Phone7 entwickelt). So wie es aussieht setzt es aber 2010 vorraus: •SP1 versions of Visual Studio 2010 Professional, Premium, Ultimate, or Express Es scheint sich aber bereits erledigt zu haben, da er heute wieder was anderes wollte . lg Gateway Zitieren Link zu diesem Kommentar Auf anderen Seiten teilen Mehr Optionen zum Teilen...
lilith2k3 Geschrieben 8. September 2011 Teilen Geschrieben 8. September 2011 aber er meint er will keine delegates (zuviel schreibarbeit). Action(T)-Delegat (System) Func(T, TResult)-Delegat (System) Dann wird's auch weniger Schreibarbeit. Zitieren Link zu diesem Kommentar Auf anderen Seiten teilen Mehr Optionen zum Teilen...
Empfohlene Beiträge
Dein Kommentar
Du kannst jetzt schreiben und Dich später registrieren. Wenn Du ein Konto hast, melde Dich jetzt an, um unter Deinem Benutzernamen zu schreiben.