2016-07-20 135 views
1

在我最近的一次採訪中,有人問我們如何在5.0版本以前的c#中實現異步編程。我回答說,通過使用代理的BeginInvoke() & EndInvoke()方法,我們可以異步調用方法。但面試官似乎並不高興。所以,當我搜索它時,有人說這是異步操作,但不是異步方法。有人可以解釋我們如何在C#5.0版本之前編寫異步方法。5.0之前的c#異步編程沒有異步&等待?

+0

[BackgroundWorker的](https://msdn.microsoft.com/en-us/library/system.componentmodel.backgroundworker(V = vs.110)的.aspx)可能是一種選擇。 –

+1

https://msdn.microsoft.com/en-us/library/jj152938(v=vs.110).aspx –

+0

@ S.Akbari感謝的快速反應。 – Jagan868

回答

0

由於C#.NET版本4.0在TPL(任務並行庫)中有類Task。任務是'期貨'或者也被稱爲'承諾'。

可以按如下方式使用它們:

Task<int> task = Task.Factory.StartNew(
    //Long Operation 
); 
    //perform other work 
int result = task.Result; 

...其中

  • task代表異步調用
  • task.Result是訪問它的結果;類似與期貨

如從Java's CompletableFuture衆所周知,TPL提供Task Continuations,在那裏你定義一個任務,要啓動的第一個任務完成後進行。

可以按如下方式使用它們:

task1. 
     ContinueWith(task2). 
      ContinueWith(task3); 

,甚至與多延續這樣的:

Task.Factory. 
    ContinueWhenAll(taskArray, continuation); 

Task.Factory. 
    ContinueWhenAny(taskArray, continuation); 

我希望這有助於你的理解。

1

異步編程有幾種歷史方法。

就BCL而言,大多數情況下跟隨Asynchronous Programming Model (APM)Event-Based Asynchronous Pattern (EAP)(APM更常見)。 EAP通常使用封面下的SynchronizationContext自動恢復「上下文」。 APM不會嘗試在「上下文」上恢復。

在EAP之前,又出現了另一個較舊的模式,很少使用,因爲它與WinForms和整個系統的整合程度過於緊密。 AFAIK,這種模式沒有名稱,但它可以通過SynchronizationObject屬性識別,您可以將其設置爲ISynchronizeInvoke(通常是WinForms控件)的實例。然後該組件在該實例的上下文中提升其事件。 BCL中這種模式的例子很少見,但有幾個:System.Timers.Timer,System.IO.FileSystemWatcherSystem.Diagnostics.Process想到。

也可以說任何一種基於事件的系統都是異步的。即使它不遵循EAP或ISynchronizeInvoke模式,任何可以在將來引發事件以通知訂戶的對象都可以被認爲是異步組件。

您可以將Rx(反應式擴展)視爲異步編程的超集。 Rx的字面意思是「事件完成正確」,因此它也可以用來實現異步組件。

最後,還有老式的回調(即持續傳遞風格 - CPS)。由於正確實施APM或EAP的複雜性,這在多年前至少在一個OSS庫中變得常見。官方的Node.js異步模式是CPS,儘管它們現在正在迅速向async/await方向發展(官方API仍然是CPS,它們被包裝在await兼容的承諾中)。無論如何,多年前有一個.NET OSS庫很常見,並且使用了CPS。我的Google-Fu讓我失望,但它可能是一個早期的HTTP客戶端?

以下是不異步編程的例子:

  • Task.Factory.StartNew
  • new Task
  • Delegate.BeginInvoke
  • ThreadPool.QueueUserWorkItem
  • new Thread
  • Task[Ex].Run

以上所有隻是調度代碼運行某處,無論是否在線程池線程,因此並不是真正的異步。描述Delegate.BeginInvoke時,只描述不同步,不正確的異步(而且很可能你的採訪混亂的原因),這是儘管MSDN文檔「asynchronous delegates」在相當混亂的術語。

假不同步是其中一個線程的行爲對待操作彷彿它是異步的,但在現實的操作僅僅是在不同的線程同步。有關真正的異步和爲什麼它不需要線程的更多信息,請參閱我的博客文章There Is No Thread