Skip to content

Instantly share code, notes, and snippets.

@Still34
Created August 20, 2017 16:59
Show Gist options
  • Save Still34/4f26babe3327dfa066ea9012c5b385c4 to your computer and use it in GitHub Desktop.
Save Still34/4f26babe3327dfa066ea9012c5b385c4 to your computer and use it in GitHub Desktop.
Concurrency testing
using System;
using System.Collections.Concurrent;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Threading.Tasks;
namespace TPLPractice
{
public class Program
{
// ReSharper disable once AsyncConverter.AsyncMethodNamingHighlighting
public static Task Main(string[] args) => new Program().StartAsync();
public async Task StartAsync()
{
Console.Clear();
var nums = new List<int>();
var result = new List<long>();
var r = new Random();
var sw = new Stopwatch();
var taskQueue = new List<Task<long>>();
for (int i = 0; i < 10; i++)
nums.Add(r.Next(10000, 500000));
Console.WriteLine(string.Join(", ", nums));
Console.WriteLine("The program will attempt to calculate the prime number for each of the numbers listed above.");
Console.WriteLine("The purpose of the test is to simulate heavy CPU workload and demonstrate each concurrent APIs.");
Console.WriteLine("Press any key to start.");
Console.WriteLine();
Console.WriteLine();
Console.ReadKey();
Console.WriteLine("Prime number calculation (foreach)");
sw.Start();
foreach (int num in nums)
result.Add(await FindPrimeNumberAsync(num).ConfigureAwait(false));
sw.Stop();
result = PrintResult(result, sw);
Console.WriteLine();
sw.Reset();
Console.WriteLine("Prime number calculation (Task.WhenAll)");
sw.Start();
taskQueue.AddRange(nums.Select(FindPrimeNumberAsync));
result.AddRange(await Task.WhenAll(taskQueue).ConfigureAwait(false));
Console.WriteLine();
taskQueue.Clear();
sw.Stop();
result = PrintResult(result, sw);
Console.WriteLine();
sw.Reset();
Console.WriteLine("Prime number calculation (Task.WhenAll, with each task wrapped in Task.Run)");
sw.Start();
taskQueue.AddRange(nums.Select(num => Task.Run(() => FindPrimeNumberAsync(num))));
result.AddRange(await Task.WhenAll(taskQueue).ConfigureAwait(false));
taskQueue.Clear();
sw.Stop();
PrintResult(result, sw);
Console.WriteLine();
sw.Reset();
Console.WriteLine("Prime number calculation (Parallel.ForEach)");
sw.Start();
result.AddRange(await CrunchNumbersForEachAsync(nums).ConfigureAwait(false));
sw.Stop();
PrintResult(result, sw);
Console.WriteLine();
sw.Reset();
Console.ReadKey();
}
public List<long> PrintResult(List<long> results, Stopwatch sw)
{
Console.WriteLine(string.Join(", ", results));
Console.WriteLine($"Finished after {sw.Elapsed}.");
results.Clear();
return results;
}
public Task<List<long>> CrunchNumbersForEachAsync(IEnumerable<int> nums)
{
var concurrentBag = new ConcurrentBag<long>();
Parallel.ForEach(nums,
async num => { concurrentBag.Add(await FindPrimeNumberAsync(num).ConfigureAwait(false)); });
return Task.FromResult(concurrentBag.ToList());
}
public Task<long> FindPrimeNumberAsync(int n)
{
int count = 0;
long a = 2;
while (count < n)
{
long b = 2;
int prime = 1;
while (b * b <= a)
{
if (a % b == 0)
{
prime = 0;
break;
}
b++;
}
if (prime > 0)
count++;
a++;
}
return Task.FromResult(--a);
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment