Ich schreibe eine Anwendung mit einer mehrschichtigen Kommunikationsschnittstelle.
Dies wurde getan, um die Kommunikation von der Benutzeroberfläche der Anwendung zu abstrahieren und sie auch skalierbarer/wartbarer zu machen.
Zum Beispiel:Umgang mit Race-Bedingungen in C#
Betrachten Sie jedes Feld in der obigen Abbildung als separate Klasse.
Das Generic Comms Interface füllt String-Variablen, die die abgewickelten Daten und die "Gesundheit" der Kommunikation beschreiben, die wiederum durch eine Reihe von öffentlichen Funktionsaufrufen in die Anwendung kopiert werden. Zum Beispiel würde die Anwendung einen Aufruf an dem App-Sub-System machen:
class Application
{
private void SomeUpdateFunction()
{
this.textBox1.AppendText(this.AppSubSystem.GetText());
}
}
class AppSubSystem
{
public string GetText()
{
return this.GenericCommsInterface.GetText();
}
}
class GenericCommsInterface
{
public string GetText()
{
string sRetVal = this.sText; // sText is populated by other functions in the class.
this.sText = null; // Suspected race condition is here.
return sRetVal;
}
}
sText
wird bevölkert asynchron durch andere Funktionen in der Klasse.
Ich glaube, dass ein Wettlauf zwischen string sRetVal = this.sText;
und der folgenden Zeile this.sText = null;
stattfindet.
Kann jemand vorschlagen, diesen Race Condition zu vermeiden oder zu verhindern? Würde StringBuilder
helfen, oder gibt es einen anderen Weg, dass ich das tun sollte?
Sehr schlecht zu 'sperren' auf ein Objekt nicht garantiert, um über den Thread-Zugang stabil zu sein - Sperren sind 'Advisory', dass jeder sie verwenden/ehren muss. Dies ist besonders schlimm, weil Sie das Sperrobjekt ständig ändern (indem Sie die Variable, die es enthält, auf null setzen). –
Guter Punkt.Ein weiterer Grund, einen StringBuilder zu verwenden. – cHao
Danke für die Tipps! Ich habe 'private string sText' durch' private StringBuilder cText' ersetzt und die Sperren implementiert. Es funktioniert super! Der Race-Zustand ist verschwunden. Kudos! –