SORU
18 ŞUBAT 2012, CUMARTESİ


C senkron yöntemi zaman uyumsuz yöntem çağrısı nasıl giderilir?

Senkron yöntemi çağırmak istiyorum public async void Foo() bir yöntem var. Şimdiye kadar MSDN belgelerine gördüğüm tüm zaman uyumsuz yöntemleri ile zaman uyumsuz yöntemleri diyor ama benim bütün program zaman uyumsuz yöntemleri ile inşa edilmiştir.

Bu mümkün olabilir mi?

Burada, zaman uyumsuz bir yöntem, bu yöntem çağırmadan bir örnek: http://msdn.microsoft.com/en-us/library/hh300224(v=vs.110).aspx

Şimdi eşitleme yöntemleri bu yöntemler zaman uyumsuz arama araştırıyorum.

CEVAP
18 ŞUBAT 2012, CUMARTESİ


Asenkron programlama "büyümek" kod tabanı ile. compared to a zombie virus olmuştur. En iyi çözüm büyümesini sağlamaktır, ama bazen bu mümkün değil.

Kısmen uyumsuz bir kod tabanı ile başa çıkmak için Nito.AsyncEx kütüphanemde birkaç türleri yazdım. Her durumda çalışan bir çözüm var.

Çözüm

Eğer içerik olarak geri eşitlemek gerek yok basit zaman uyumsuz bir yöntem varsa, o zaman Task.WaitAndUnwrapException kullanabilirsiniz:

var task = MyAsyncMethod();
var result = task.WaitAndUnwrapException();

Yaparsındeğilonlar AggregateException istisnalar kaydırmak için Task.Wait Task.Result kullanmak istiyor.

Bu çözüm ise MyAsyncMethod geri içerik olarak senkronize değilse uygun değil sadece. Diğer bir deyişle, MyAsyncMethod 11 ** her 13 *ile bitmelidir. Bu herhangi bir kullanıcı arabirimi öğeleri güncelleştirmek ya ASP.NET istek içeriği erişim anlamına gelir.

Çözüm B

Eğer MyAsyncMethod içerik olarak geri eşitlemek için ihtiyacı varsa, o zaman AsyncContext.RunTask iç içe geçmiş bir bağlam sağlamak için kullanmak mümkün olabilir:

var result = AsyncContext.RunTask(MyAsyncMethod).Result;

*Güncelleme 4/14/2014: API kütüphane daha yeni sürümleri

var result = AsyncContext.Run(MyAsyncMethod);

(RunTask Task istisnalar yaymak çünkü TAMAM bu örnekte Task.Result kullanmak için).

AsyncContext.RunTask Task.WaitAndUnwrapException yerine gerekebilir sebebi Win/WPF/SL/ASP olur oldukça ince bir kilitlenme ihtimali yüzünden.NET:

  1. Zaman uyumlu bir yöntem zaman uyumsuz bir yöntem, Task bir elde çağırır.
  2. Senkron yöntemi Task engelleme bir süre bekleyebilir.
  3. async yöntemi ConfigureAwait olmadan await kullanır.
  4. Task tamamlayamıyor bu durum, çünkü sadece zaman tamamlar async yöntem tamamlandı; async yöntem tamamlayamıyor çünkü çalışan zamanlama devamı için SynchronizationContext ve Win/WPF/SL/ASP.NET senkron yöntemi zaten bu bağlamda çalıştığı için devamı çalıştırmak için izin vermez.

Bu iyi bir fikir async her yöntem içinde ConfigureAwait(false) mümkün olduğunca kullanmak bir nedeni de budur.

Çözüm C

AsyncContext.RunTask her senaryoda işe yaramaz. Eğer async yöntemi tamamlamak için bir kullanıcı arabirimi olay gerektiren bir şey bekliyor, örneğin, daha sonra iç içe kapsamında bile çıkmaz. Bu durumda, iş parçacığı havuzu async yöntemi başlayabilirsin:

var task = TaskEx.RunEx(async () => await MyAsyncMethod());
var result = task.WaitAndUnwrapException();

Ancak, bu çözüm, iş parçacığı havuzu bağlamında çalışacak MyAsyncMethod gerektirir. UI öğeleri güncelleştirmek ya ASP.NET istek içeriği erişememesi. Ve bu durumda da await tablolar ConfigureAwait(false) ekleyin ve çözüm A. kullanabilirsiniz

Bunu Paylaş:
  • Google+
  • E-Posta
Etiketler:

YORUMLAR

SPONSOR VİDEO

Rastgele Yazarlar

  • Andrea Lewis

    Andrea Lewis

    14 Mart 2013
  • DetroitBORG

    DetroitBORG

    29 Temmuz 2008
  • Rickymon Tero

    Rickymon Ter

    1 Ocak 2007