#c# #asynchronous
#c# #асинхронный
Вопрос:
Я хочу сохранить результаты асинхронных запущенных задач в частном словаре. Когда я использую add, я получаю исключение с нулевой ссылкой. Что я должен изменить, чтобы правильно заполнить словарь?
Вот мой код, который я получил до сих пор:
private Dictionary<string, long> _filesDictionary;
public void GetFiles(string pathToFolder)
{
var allDirectories = Directory.EnumerateDirectories(pathToFolder, "*", SearchOption.AllDirectories);
allDirectories.ToList().Add(pathToFolder);
foreach (var dir in allDirectories)
{
FolderReading(dir);
}
}
public void FolderReading(string folderPath)
{
string[] fileSystemEntries = Directory.GetFileSystemEntries(folderPath);
if (fileSystemEntries.Count() != 0)
{
List<Task> tasks = new List<Task>();
foreach (var filePath in fileSystemEntries.OrderBy(s => s))
{
Task task = Task.Run(() => CountSizes(filePath));
tasks.Add(task);
}
Task.WaitAll(tasks.ToArray());
}
}
private void CountSizes(string filePath)
{
byte[] fileData = null;
int arraySum = 0;
string fileName = Path.GetFullPath(filePath);
using (FileStream fs = File.OpenRead(filePath))
{
using (BinaryReader binaryReader = new BinaryReader(fs))
{
fileData = binaryReader.ReadBytes((int)fs.Length);
}
}
foreach (byte b in fileData)
{
arraySum = b;
}
Console.WriteLine($"{fileName} ArraySum{arraySum}; ThreadNum:{Thread.CurrentThread.ManagedThreadId}");
_filesDictionary.Add(fileName, arraySum);
}
Ответ №1:
You’re _filesDictionary
никогда не создается, только объявляется, что означает, что в этом случае он всегда будет иметь значение по умолчанию null
. Где-то в вашем коде вам нужно присвоить ему значение. Обычно это делается в конструкторе класса, но вы также можете сделать это прямо в объявлении.
Конструктор:
_filesDictionary = new Dictionary<string, long>();
Объявление:
private Dictionary<string, long> _filesDictionary = new Dictionary<string, long>();
Редактировать: только сейчас заметил, что вы используете несколько задач для добавления в словарь, но имейте в виду, что defualt Dictionary
не является полностью потокобезопасным. Это означает, что чтение из словаря из нескольких задач (возможно, в разных потоках выполнения) в порядке, но запись в него невозможна, поскольку это может привести к скачкам данных и недопустимым добавлениям. Вместо этого вам нужно будет использовать .NET’s ConcurrentDictionary