Ich versuche Token zu verwenden, um Task abgebrochen von Task.Run gestartet. Ich nahm Muster von Microsoft-Website: https://msdn.microsoft.com/pl-pl/library/hh160373(v=vs.110).aspxProgramm werfen OperationCanceledException trotz abfangen
Dies ist mein Code:
public static class Sender
{
public static async Task sendData(NetworkController nc) {
await Task.Run(() => {
IPEndPoint endPoint = new IPEndPoint(nc.serverIp, nc.dataPort);
byte[] end = Encoding.ASCII.GetBytes("end");
while (true) {
if (Painting.pointsQueue.Count > 0 && !nc.paintingSenderToken.IsCancellationRequested) {
byte[] sendbuf = Encoding.ASCII.GetBytes(Painting.color.ToString());
nc.socket.SendTo(sendbuf, endPoint);
do {
sendbuf = Painting.pointsQueue.Take();
nc.socket.SendTo(sendbuf, endPoint);
} while (sendbuf != end && !nc.paintingSenderToken.IsCancellationRequested);
}
else if (nc.paintingSenderToken.IsCancellationRequested) {
nc.paintingSenderToken.ThrowIfCancellationRequested();
return;
}
}
}, nc.paintingSenderToken);
}
}
Und hier beginne ich diese Aufgabe:
public void stopController() {
try {
paintingSenderTokenSource.Cancel();
senderTask.Wait();
} catch(AggregateException e) {
string message = "";
foreach (var ie in e.InnerExceptions)
message += ie.GetType().Name + ": " + ie.Message + "\n";
MessageBox.Show(message, "Przerwano wysylanie");
}
finally {
paintingSenderTokenSource.Dispose();
byte[] message = Encoding.ASCII.GetBytes("disconnect");
IPEndPoint endPoint = new IPEndPoint(serverIp, serverPort);
socket.SendTo(message, endPoint);
socket.Close();
mw.setStatus("disconnected");
}
}
public async void initialize() {
Task t = Reciver.waitForRespond(this);
sendMessage("connect");
mw.setStatus("connecting");
if (await Task.WhenAny(t, Task.Delay(5000)) == t) {
mw.setStatus("connected");
Painting.pointsQueue = new System.Collections.Concurrent.BlockingCollection<byte[]>();
senderTask = Sender.sendData(this);
}
else {
mw.setStatus("failed");
}
}
}
In initialize()
Methode, die ich bin auf die Antwort von der Warte Server und wenn ich es bekomme, starte ich einen neuen Thread in dieser sendData()
Methode. Es ist in der statischen Klasse, Code sauberer zu machen. Wenn ich diesen Thread stoppen möchte, rufe ich stopController()
Methode. In Microsoft-Website können wir lesen:
Die CancellationToken.ThrowIfCancellationRequested Methode löst eine OperationCanceledException Ausnahme, die in einem catch-Block behandelt wird, wenn der aufrufende Thread die Task.Wait Methode aufruft.
Aber mein Programm bricht auf nc.paintingSenderToken.ThrowIfCancellationRequested();
, die in ‚senddata()‘ Methode ist und der Fehler sagt, dass OperationCanceledException nicht behandelt wurde. Ich habe das Programm von Microsoft Website gestartet und es funktioniert perfekt. Ich denke, ich mache alles wie sie, aber leider funktioniert es nicht so, wie es sollte.
Schnelle Frage, haben Sie "Aktivieren Sie nur meinen Code" aktiviert? – WBuck
Ja, ich habe es aktiviert. – Dzejkob