2011-02-15 12 views
5

VB.NET 2010, .NET 4VB.NET Genel çapraz iş parçacıklı işlemlere iki farklı yaklaşım; Hangisi daha iyi?

Merhaba,

Son zamanlarda bazı kodlar için yürütme iş parçacığını denetlemek için SynchronizationContext nesneleri kullanma hakkında okudum. Xzx65 kullanan UI denetimlerini güncelleştirme gibi şeyler için çapraz iş çağrıları (muhtemelen) işlemek için genel bir alt yordamı kullanıyorum. Ben amatörüm ve belirli bir yaklaşımın artılarını ve eksilerini anlamakta zorlanıyorum. Hangi yaklaşımın tercih edilebileceğine ve neden tercih edileceğine dair bir anlayış arıyorum.

Güncelleme: Bu soru kısmen MSDN page on Control.InvokeRequired adresinden gelenler gibi ifadelerle motive edilmiştir.

Daha da iyi bir çözüm, SynchronizationContext tarafından döndürülen SynchronizationContext 'ı çapraz-iplikli sıralama için bir kontrolünden ziyade kullanmaktır.

Ayrıca, etrafa baktığımda, SO üzerinde bu tür bir soruna ilişkin soruların cevaplarının çoğunun neden bu yöntemi belirtmeden Invoke yaklaşımını önerdiğine dair genel karışıklık.

Public Sub InvokeControl(Of T As Control)(ByVal Control As T, ByVal Action As Action(Of T)) 
    If Control.InvokeRequired Then 
     Control.Invoke(New Action(Of T, Action(Of T))(AddressOf InvokeControl), New Object() {Control, Action}) 
    Else 
     Action(Control) 
    End If 
End Sub 

Yöntem 2:

Public Sub UIAction(Of T As Control)(ByVal Control As T, ByVal Action As Action(Of Control)) 
    SyncContext.Send(New Threading.SendOrPostCallback(Sub() Action(Control)), Nothing) 
End Sub 

Burada SyncContext, UI formumun yapıcısında tanımlanmış bir Threading.SynchronizationContext nesnesidir (bir modülde saklıyorum ... Emin değilim Eğer en iyi seçenek buysa):

Public Sub New() 
    InitializeComponent() 
    SyncContext = WindowsFormsSynchronizationContext.Current 
End Sub 

Daha sonra, UI formundaki bir denetimi (örn. Label1) güncellemek isteseydim:

InvokeControl(Label1, Sub(x) x.Text = "hello") 

veya

UIAction(Label1, Sub(x) x.Text = "hello") 

Peki, sen ne düşünüyorsun? Bir yol tercih edilir mi yoksa içeriğe mi bağlı? Zamanınız varsa, ayrılık takdir edilecektir!

Şimdiden teşekkürler,
Brian

cevap

4

Sanırım herhangi bir yanıt alamıyorum çünkü, ben içeren kendi soruya kısmi bir cevap başlatmak düşündüm, bazı okuma yapıyor ve bu muydu Şimdiye kadar bulabildim:

interesting codeproject article ileti dizisini, (özellikle çalışan iş parçacıklarından UI iş parçacığına kadar) iş parçacığı arasında kodlama kodu için SynchronizationContext kullanımını tartıştım. Bazı gözlemler Ben ilginç buldum:

  • UI parçacığının SynchronizationContext nesne bu başlık altındaki ilk kontrolün oluşturulduktan sonra oluşturulur. Bundan önce tanımlanmadı.
  • UI dizisi için SynchronizationContext, SynchronizationContext sınıfının bir örneği değil, SynchronizationContext türetilmiş System.Windows.Forms.WindowsFormsSynchronizationContext sınıfının örneğidir. Post/Send'un davranışını tanımlayan bu sınıf, kodun bir iş parçacığından diğerine sıralanmasına izin verir.
  • Invoke'u kullanmak yerine UI iş parçacığının SynchronizationContext'u iletme konusundaki bir itiraz, çağırmak için mantıksal UI formunuza bir başvuru tutmak zorunda kalmamanızdır.
  • Post yöntemi, engelleme olmadığı için gösterge güncelleştirmeleri gibi şeyleri gerçekleştirmek için çekici görünüyor, ancak makalenin işaret ettiği gibi, gönderilen kodda atılan istisnalar UI iş parçacığına atılır. diğer bir deyişle, kullanıcı arayüzüne gönderilen koddaki bir hata, kullanıcı arayüzünü çarpabilir. Send, bu sorun yok. Gönderirken atılan istisnalar iş parçacığına atılır.

Güncelleme: İşte another insightful article olduğunu. Bu yazıda, Kael Rowan, SynchronizationContext'un bir kontrol örneğinin Invoke/BeginInvoke yöntemlerine tercih edilebileceği bir bağlamı ele almaktadır. Yeniden kullanılabilir bir kütüphane yazarken, kütüphane dışındaki bir kontrolün sadece çağırma amaçlı bir referansa sahip olması gerekmediğini savunur. Oluşturulan herhangi bir yeni iş parçacığının UI iş parçacığının SynchronizationContext paylaşacağı bir temsilci için kod sağlar.

Pekala, burada daha fazla yorum almayacağım gibi görünüyor. Burada yazdıklarım, cehaletim bir cevaba ulaşmama izin verdiği kadar yakın. Ekleyecek başka bir şey varsa, kesinlikle bunu takdir ediyorum, ama şimdilik devam ediyorum. :/

İlgili konular