Your sample code is using i at the time of execution which is 50. It has to do with closures. Task.Run() is the recommended approach.
public class MyClass
{
ConcurrentDictionary<int, int> _numbers = new ConcurrentDictionary<int, int>();
public MyClass() { }
public async Task CallMeAsync()
{
_numbers.Clear();
_numbers.TryAdd(99, 100);
int threadCount = 50;
Task[] tasks = new Task[threadCount];
for (int i = 0; i < threadCount; i++)
{
int j = i;
tasks[j] = Task.Run(() => AddToDict(j));
}
await Task.WhenAll(tasks);
foreach (KeyValuePair<int, int> item in _numbers)
Console.WriteLine("Key: " + item.Key.ToString() + "; Value: " + item.Value.ToString());
}
private void AddToDict(int number)
{
if(!_numbers.TryAdd(number, number + 1))
{
Console.WriteLine("Not added - Key {0} Value {1} ", number, number + 1);
}
}
}
Implementation (.NET 5)
class Program
{
static async Task Main(string[] args)
{
MyClass myClass = new MyClass();
await myClass.CallMeAsync();
}
}