2012-10-01 16 views
6

私はクライアントまたはサービスでAsync-Awaitを適用することに関連してthis質問を投稿しました。質問と密接に結びついているので、この質問を先に進む前に質問をお読みください。Async-Awaitの本当の利点は?

私はC#4.0(TPL)とC#5.0(Async - Await)のコードをテストしました。サービスで提供されるメソッドの非同期バージョンと同期バージョンを使用してサービスを呼び出し、それぞれの場合に使用されるスレッドの数を比較しています。続き は私が使用したリソースをテストするために使用しているコードです:

mainメソッド

List<Task<string>> tasksList = new List<Task<string>>(); 
List<int> asyncThreads = new List<int>(); 
List<int> tplThreads = new List<int>(); 
Stopwatch watch = new Stopwatch(); 
watch.Start(); 

// Call the Async version of the method 
for (int i = 0; i < 500; i++) 
{ 
    tasksList.Add(GetNameFromServiceAsync("Input" + i.ToString(), asyncThreads)); 
} 

Task.WaitAll(tasksList.ToArray()); 

watch.Stop(); 

foreach (var item in asyncThreads.Distinct()) 
{ 
    Console.WriteLine(item); 
} 

Console.WriteLine("(C# 5.0)Asynchrony Total Threads = " + asyncThreads.Distinct().Count()); 
Console.WriteLine(watch.ElapsedMilliseconds.ToString()); 

watch.Restart(); 

tasksList.Clear(); 

// Call the normal method 
for (int i = 0; i < 500; i++) 
{ 
    tasksList.Add(GetNameFromService("Input" + i.ToString(), tplThreads)); 
} 

Task.WaitAll(tasksList.ToArray()); 

watch.Stop(); 

foreach (var item in tplThreads.Distinct()) 
{ 
    Console.WriteLine(item); 
} 

Console.WriteLine("(C# 4.0)TPL Total Threads" + tplThreads.Distinct().Count()); 

Console.WriteLine(watch.ElapsedMilliseconds.ToString()); 

非同期および同期は私がきた今

static async Task<string> GetNameFromServiceAsync(string name, List<int> threads) 
{ 
    Console.WriteLine(" Start Current Thread : " + System.Threading.Thread.CurrentThread.ManagedThreadId); 
    var task = await client.GetNameAsync(name); 
    threads.Add(System.Threading.Thread.CurrentThread.ManagedThreadId); 
    // Console.WriteLine("End GetNameFromServiceAsync Current Thread : " + System.Threading.Thread.CurrentThread.ManagedThreadId); 
    return task; 
} 

static Task<string> GetNameFromService(string name, List<int> threads) 
{ 

    var task = Task<string>.Factory.StartNew(() => 
     { 
      threads.Add(System.Threading.Thread.CurrentThread.ManagedThreadId); 
     // Console.WriteLine("GetNameFromService Current Thread : " + System.Threading.Thread.CurrentThread.ManagedThreadId); 
      return client.GetName(name); 
     }); 

    return task; 
} 

サービスへの呼び出し答えに取り組み、結果は以下のとおりです。

  • サービスを500回呼び出すと、スレッドは4-5個しか使用されません。
  • TPLコールは、約44〜45スレッドを生成します。
  • 非同期呼び出しの時間は約17 - 18秒です。
  • TPL呼び出しの時間は約42-45秒です。

他のコミュニティメンバーにも役立つように、私の調査結果にフィードバックをしたいと思います。それは私の以前の質問の答えは何ですか?私の観察Q.

EDIT

たちは非同期待つ代わりにTPLのTask.Factory.startNewを使用している場合、それはあまりのスレッドを消費しますと結論づけています。これはどうですか?そうでない場合、そのような比較を行うために正しい方向は何ですか?

Q.私はasyncを学んでいるので、私は何らかの比較とソリッドコードでその価値を証明したいと思います。

+8

あなたの質問は何ですか? –

+0

asyncを使用することで、メモリの利点が得られます(リソースが少なくなります)。これは私が以前の質問から得たもの、または私が理解したもので、私が知りたいのはこれの答えです。 async-awaitを使用することでスケーラビリティのメリットを尋ねたいと思います。私は結論したものとインラインですか? –

+0

重要な利点の1つは、ユーザーが同期コードを実行したときに非同期の問題に直面したとは言えないという明示的な利点です。 –

答えて

12

クライアント側async(同期コードと比較して)は、メモリのわずかのコストで応答性を改善します。

(同期コードと比較して)サーバー側のasyncは、一般的に、メモリ/スレッドの使用を減らすことによってスケーラビリティを向上させます。これらの利点は、クライアントサイドasync(マルチスレッドコードと比較して)にも当てはまります。

これらはどちらも極端な一般化であり、間違っている状況があります。

更新:

私の観察は、我々は非同期待つ...を使用している場合、それはあまりのスレッドを消費しますと結論づけています。

async/awaitメンテナンス可能な非同期コードを有効にします。それ自身では、スレッドの作成とは何の関係もありません。ただし、多くの場合、バックグラウンドタスクを作成するのにTask.Run(またはTask.Factory.StartNew)と一緒に使用されます。

私はasync-awaitを学習しているので、何らかの比較とソリッドコードでその価値を証明したいと思います。

asyncおよびawaitはコンパイラ変換です。非同期プログラムを書くのが簡単になりました。それだけです。

これらを同期コードと比較すると、通常、応答性やスケーラビリティが向上します。それらを既存の非同期コードと比較すると、通常はとなります。は効率が劣りますが、コードの保守性の面でそれを補うものです。

+0

ステファンありがとうございます。私は自分の質問を更新しました。 –

+0

答えを更新しました。 –