Перезапись файла с помощью StreamWriter C#
Есть проблема Определён StreamReader
using (StreamReader reader = new StreamReader(PathManager.PathUserID))
В этом using есть другой блок using
using (StreamWriter write = new StreamWriter(PathManager.PathUserID))
{
List<string> userID = new List<string>();
while ((ID = reader.ReadLine()) != null)
{
if (ID == message.Chat.Id.ToString())
{ continue; }
userID.Add(ID);
}
write.Write(string.Join(Environment.NewLine, userID));
}
Смысл такой: Имеется файл с ID пользователей по полю PathManager.PathUserID
Блок с StreamWriter write вызывается тогда, когда пользователь хочет отписаться от рассылки, должно происходить это следующим образом:
Список userID нужен для того, чтобы добавить все ID в него из файла, кроме ID того пользователя, который хочет отписаться
это как раз делает блок while, когда видит совпадающие ID, он его просто не добавляет
В конце всё записывается в файл с переносом строки с помощью write.Write(string.Join(Environment.NewLine, userID));
Но происходит просто удаление всех записей из файла и всё
Как исправить данную проблему?
Ответы (1 шт):
У файловых потоков есть множество параметров, такие как FileShare, FileAccess и другие. Чтобы один и тот же поток (stream) мог одновременно использоваться разными читателями/писателями, нужно правильно задать эти параметры.
Минимум нужно указать следующее: reader разрешает (расшаривает доступ) другим средствам писать (FileShare.Write) в этот же поток, а writer'у нужно явно задать доступ на запись (FileAccess.Write).
string? line;
using (StreamReader reader = new StreamReader(path, new FileStreamOptions { Share = FileShare.Write }))
using (StreamWriter writer = new StreamWriter(path, new FileStreamOptions { Access = FileAccess.Write }))
{
List<string> ids = new List<string>();
while ((line = reader.ReadLine()) != null)
{
if (line != value)
ids.Add(line);
}
writer.Write(string.Join(Environment.NewLine, ids));
}
Однако, если получившийся результат будет короче исходного содержимого, то в конце файла останется мусор. К тому же может влиять наличие BOM...
Подробное описание вы явно воспримете как rocket science, а вы, судя по уже удалённым комментариям, не стремитесь к звёздам.
Гораздо проще поступить следующим образом: открываем поток на чтение, полностью читаем, закрываем, открываем поток на запись, пишем, закрываем.
При это нет необходимости задумываться о правилах расшаривания и доступа, не будет лишнего мусора.
string? line;
List<string> ids = new List<string>();
using (StreamReader reader = new StreamReader(path))
{
while ((line = reader.ReadLine()) != null)
{
if (line != value)
ids.Add(line);
}
}
using (StreamWriter writer = new StreamWriter(path))
{
writer.Write(string.Join(Environment.NewLine, ids));
}
Я бы предложил более простой способ:
var ids = File.ReadLines(path).Where(line => line != value).ToList();
File.WriteAllLines(path, ids);
но вы явно воспримете его как критику своего кода, что вы не любите...