Форум программистов, компьютерный форум, киберфорум
C# Windows Forms
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.60/5: Рейтинг темы: голосов - 5, средняя оценка - 4.60
HF
 Аватар для HF
1316 / 895 / 200
Регистрация: 09.09.2011
Сообщений: 2,691
Записей в блоге: 2

Как интегрировать ProgressBar при работе с IEnumerable?

04.05.2019, 00:38. Показов 1007. Ответов 3

Студворк — интернет-сервис помощи студентам

Не по теме:

Не думал что когда-то задам подобные вопросы, но столкнулся с такой проблемкой и решил долго не гуглить, а спросить знающих.
Предыстория. Была у меня программа, написанная 8 лет назад. "Лапшекод", но чудно рабочий. Решил я её переписать, правильно, с учётом всем современных тенденций и веяний. Заодно потренироваться в формах.


Сценарий работы.
Задача: Исходный текстовый файл сконвертировать в другой текстовый файл.
Одна строка исходного файла - структурированная (например csv). Файл результата - "выжимка" из источника, с различными изменениями.

Текущая реализация: Форма, кнопка. Сгенерировать файл.
Жмём, выбираем файл для загрузки, жмём ОК. Смотрим строку прогресса и окно результата.
Проверяем - создался новый файл.

Так как всё было без потоков, написано в одном методе. То и проблем с тем, чтобы обновить статусбар конечно же не было (как и с другими сложностями, которые возможно в процессе описания тоже будут упомянуты).

Новая реализация:
T1 - модель исходного файла, T2 - модель конечного файла
Загрузка и запись сделаны через простейшие методы: File.ReadLines/WriteAllLines, которые умеют работать с IEnumerable.
  • Вызываем метод GenerateT2 из сервиса T2. Метод загрузки файла. Получает имя.
  • Вызывается метод сервиса T1 для загрузки исходного файла. Загружается в виде IEnumerable<string>, делает конвертацию в T1 и отдаёт IEnumerable<T1>.
  • Конвертируем в T2 и отдаёт IEnumerable<T2>.
Готово. У нас есть результат для записи. Сохраняем в конечный файл.

Вопрос: Как можно интегрировать ProgressBar?
В случае с IEnumerable мы не знаем ничего о размере.
И, даже зная размер исходного файла, я не могу контролировать процесс "перебора".

Как вариант:
Получаю размер коллекции (пусть, я могу сделать .Count()). Тогда процесс записи нужно реализовать через отдельный метод. Например через StreamWriter записывать строки, и через созданный счётчик считать пройденное количество, сравнивая с общим. Сомнения:
- выполняя .Count и потом запись - я же по сути считаю весь файл в память. А не два ли раза прочитаю в итоге?
- и как мне передавать общий каунтер, если метод сохранения находится в сервисе и он знать не должен про такие параметры. Или именно в этом методе и выполнить .Count() ?

Комментарии. Почему сделал так?
- Так как хотел сделать по уму, то разбивал всё для работы с UnitTest.
- IEnumerable выбрал с целью поддержки очень большого исходного файла. Чтобы не читать всё в большую коллекцию.
0
cpp_developer
Эксперт
20123 / 5690 / 1417
Регистрация: 09.04.2010
Сообщений: 22,546
Блог
04.05.2019, 00:38
Ответы с готовыми решениями:

Как плавно заполнять "progressBar" при работе таймера?
Как плавно заполнять &quot;progressBar&quot; при работе таймера? Например: из 5 минутной задержки прошло 2,5 мин. &quot;progressBar&quot; заполнился...

Ошибка при использовании IEnumerable<T>: Использование универсального типа IEnumerable требует аргумент типа 1
Доброго Вам времени суток. Помогите решить следующую задачку. На строке IEnumerable&lt;Device&gt; = deviceContext.Devices; возникает...

Сделать преобразование из string в IEnumerable<XElement>, или как в IEnumerable<XElement> формировать команду?
такая команда работает var v= xDoc.Root.Elements(&quot;root&quot;).Elements(&quot;file&quot;).Elements(&quot;valuta&quot;).Elements(); как её же сформировать...

3
HF
 Аватар для HF
1316 / 895 / 200
Регистрация: 09.09.2011
Сообщений: 2,691
Записей в блоге: 2
04.05.2019, 20:18  [ТС]
Если так никто не делает, то я с удовольствием послушаю как это делают или рекомендуют. Если я написал сложно, напишите, я перефразирую. Но как то странно, что нет ни одной мысли.

У меня появился интересный вариант. Если сделать файловый менеджер на Stream шаблоне. Тогда я смогу мониторить позицию при чтении и записи.
0
Эксперт .NET
6691 / 4102 / 1607
Регистрация: 09.05.2015
Сообщений: 9,575
04.05.2019, 20:38
Цитата Сообщение от HF Посмотреть сообщение
У меня появился интересный вариант. Если сделать файловый менеджер на Stream шаблоне. Тогда я смогу мониторить позицию при чтении и записи.
Тот же StreamReader/Writer может вам вернуть позицию. На нем и сделайте если вам так уж нужен прогресс бар.

Что нибудь типа
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
    class TextFileEnumerator : IDisposable, IEnumerable<string>
    {
        private StreamReader reader;
 
        public long Position => reader.BaseStream.Position;
        public long Length => reader.BaseStream.Length;
 
        public TextFileEnumerator(string file)
        {
            reader = new StreamReader(file);
        }
 
        public void Dispose() => reader?.Dispose();
 
        public IEnumerator<string> GetEnumerator()
        {
            while(!reader.EndOfStream)
                yield return reader.ReadLine();
        }
 
        IEnumerator IEnumerable.GetEnumerator() => GetEnumerator();
    }
C#
1
2
3
4
5
6
7
            TextFileEnumerator sr = new TextFileEnumerator("file.txt");
            
            foreach (string line in sr)
            {
                Console.Write($"\r{sr.Position * 100f / (sr.Length):F2}: {line}");
            }
            Console.ReadKey();
1
HF
 Аватар для HF
1316 / 895 / 200
Регистрация: 09.09.2011
Сообщений: 2,691
Записей в блоге: 2
04.05.2019, 21:27  [ТС]
Цитата Сообщение от Someone007 Посмотреть сообщение
Тот же StreamReader/Writer может вам вернуть позицию.
Да, именно так моя мысль и выглядела. Stream, StreamReader, .. - детали.

Цитата Сообщение от Someone007 Посмотреть сообщение
TextFileEnumerator sr = new TextFileEnumerator("file.txt");foreach (string line in sr)
Вот это точно не тот вариант. Если я сделаю (как уже сделано) sr.Select(a => a) то ни о каком подобном чтении позиции не будет и речи.
Мне нужно будет использовать подписку на событие внутри этого TextFileEnumerator, которое будет возвращать позицию.
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
raxper
Эксперт
30234 / 6612 / 1498
Регистрация: 28.12.2010
Сообщений: 21,154
Блог
04.05.2019, 21:27
Помогаю со студенческими работами здесь

Как в WP интегрировать XENFORO (чтоб общее меню было у сайта и при переходе на форум)
Друзья ПОМОГИТЕ!!! -На сайте стоит форум bbpres+WP интеграция ( При переходе между сайтом и форумов-меню остается одно и тоже и всё одно...

Цикл foreach, проход по IEnumerable и IEnumerable.ToList()
Здравствйте, уважаемые форумчане, вопрос по реализации цикла foreach. Два куска кода: foreach (var variable in...

Проверить корректность реализации IEnumerable<T> и IEnumerable
Гуру, выручайте! Разбираюсь в создании обобщенной коллекции и запутался в том, как реализовать интерфейсы IEnumerable&lt;T&gt; и...

Как отобразить ProgressBar при загрузке формы
Конечно неудобно писать первый раз открыл с# хочу сделать загрузку и по оканчанию неё открувалась бы новая форма но что то немного не...

Как сделать ProgressBar при запуске программы
При первом запуске программы грузится информация из интернета и это занимает некоторое время (все происходит на мейн форме). Как сделать в...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
4
Ответ Создать тему
Новые блоги и статьи
Жизнь в неопределённости
kumehtar 23.03.2026
Жизнь — это постоянное существование в неопределённости. Например, даже если у тебя есть список дел, невозможно дойти до точки, где всё окончательно завершено и больше ничего не осталось. В принципе,. . .
Модель здравоСохранения: работники работают быстрее после её введения.
anaschu 23.03.2026
geJalZw1fLo Корпорация до введения программа здравоохранения имела много невыполненных работниками заданий, после введения программы количество заданий выросло. Но на выплатах по больничным это. . .
1С: Контроль уникальности заводского номера
Maks 23.03.2026
Алгоритм контроля уникальности заводского (или серийного) номера на примере документа выдачи шин для спецтехники с табличной частью. Данные берутся из регистра сведений, по которому настроено. . .
Хочу заставить корпорации вкладываться в здоровье сотрудников: делаю мат модель здравосохранения
anaschu 22.03.2026
e7EYtONaj8Y Z4Tv2zpXVVo https:/ / github. com/ shumilovas/ med2. git
1С: Программный отбор элементов справочника по группе
Maks 22.03.2026
Установка программного отбора элементов справочника "Номенклатура" из модуля формы документа. В качестве фильтра для отбора справочника служит группа номенклатуры. Отбор по наименованию группы. . .
Как я обхитрил таблицу Word
Alexander-7 21.03.2026
Когда мигает курсор у внешнего края таблицы, и нам надо перейти на новую строку, а при нажатии Enter создается новый ряд таблицы с ячейками, то мы вместо нервных нажатий Энтеров мы пишем любые буквы. . .
Krabik - рыболовный бот для WoW 3.3.5a
AmbA 21.03.2026
без регистрации и смс. Это не торговля, приложение не содержит рекламы. Выполняет свою непосредственную задачу - автоматизацию рыбалки в WoW - и ничего более. Однако если админы будут против -. . .
1С: Программный отбор элементов справочника по значению перечисления
Maks 21.03.2026
Установка программного отбора элементов справочника "Сотрудники" из модуля формы документа. В качестве фильтра для отбора служит значение перечислений. / / Событие "НачалоВыбора" реквизита на форме. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru