|
|
Регистрация Восстановить пароль |
Регистрация | Задать вопрос |
Заплачу за решение |
Новые сообщения |
Сообщения за день |
Расширенный поиск |
Правила |
Всё прочитано |
|
|
Опции темы | Поиск в этой теме |
25.02.2013, 13:01 | #1 |
Пользователь
Регистрация: 23.04.2011
Сообщений: 42
|
Out of memory и правильная работа с памятью
Всем привет!
Опять взялся за свою старую идею - написать софтинку, которая будет удалять одинаковые записи из файла. Еще на самых первых шагах меня предупреждали, что в конце концов я нарвусь на ошибку Out of memory, так вот я на нее и нарвался. Сама ошибка возникает только на больших файлах, да и то не всегда. Даже один и тот же файл может как отработать без этой ошибки, так и с ошибкой на разных этапах обработки. Если же запускать кучу файлов, то ошибка возникает со 100% вероятностью. Много чего почитал для борьбы с этой ошибкой, вроде даже что-то переделал, но все-равно не помогает. Очень прошу помощи!!! Вот код (с комментариями конечно): Код:
Пока для себя выяснил, что ошибка может возникать как при первом заполнении массива, так и на следующих. |
25.02.2013, 13:30 | #2 | |
Старожил
Регистрация: 09.01.2008
Сообщений: 26,229
|
Цитата:
Код:
|
|
25.02.2013, 13:37 | #3 |
Пользователь
Регистрация: 23.04.2011
Сообщений: 42
|
Хм, если честно - не знал... Спасибо, за совет!!!
Но проблему это конечно не решает. |
25.02.2013, 13:53 | #4 | ||
Старожил
Регистрация: 09.01.2008
Сообщений: 26,229
|
Цитата:
например, Цитата:
ну и максимальное число записей в 10 миллионов - впечатляет! А чего мелочитесь? Чего не 10 миллиардов? (я имею в виду, что большие объёмы данных нужно обрабатывать частями...) |
||
25.02.2013, 13:59 | #5 |
Форумчанин
Регистрация: 11.03.2011
Сообщений: 426
|
А не проще всё это решать через SQL и ADO, который под такие задачи и заточен?
|
25.02.2013, 14:05 | #6 |
Пользователь
Регистрация: 23.04.2011
Сообщений: 42
|
Да 10 миллионов я поставил уже в самом конце - тесты вел от 1000. Раньше то проблема была больше в скорости чтения файла и вроде как 10 млн с одной стороны неплохо подходит для больших файлов, с другой это суммарно по объему памяти не так много. Просто читать файл в 30-40 млн по 10 тысяч медленно. А грузить весь тоже не вариант - точно попаду на ошибку.
Объект, который создается строчкой Код:
Код:
Попробую поискать утечку... |
25.02.2013, 14:12 | #7 | |
Старожил
Регистрация: 17.11.2010
Сообщений: 18,922
|
Цитата:
Если бы архитекторы строили здания так, как программисты пишут программы, то первый залетевший дятел разрушил бы цивилизацию
|
|
25.02.2013, 14:18 | #8 |
Старожил
Регистрация: 20.04.2008
Сообщений: 5,528
|
а зачем вообще этот массив?
только для того чтобы "буферизовать" чтение данных из файла(с HDD) в Dictionary? Но он уже и так буферизован. HDD(источник) -> Stream(свой буфер!) -> Array(наш буфер!) -> Dictionary(место назначения) читайте из Stream по одной записи и будет вам счастье! (и код проще). Вы все равно не читаете здесь из файла, а только переносите данные из одного места в памяти (буфер Stream) в другое (данные Dictionay) через третий фрагмент памяти (array). Буферизация обычно вначале фиксирует размер буфера (а иногда и сами буфера). Откажитесь от "бесконечных" setLength. Задайте размер раз и навсегда. И просто следите за тем какая часть массива заполнена. (учитывая предыдущее замечание оптимальный размер =1).
программа — запись алгоритма на языке понятном транслятору
Последний раз редактировалось evg_m; 25.02.2013 в 14:30. |
25.02.2013, 14:22 | #9 | |
Старожил
Регистрация: 09.01.2008
Сообщений: 26,229
|
Цитата:
Но уж, в любом случае, нужно делать что-то одно, явно не стоит указателю, которому присвоен nil уже после присвоения вызывать процедуру выделения памяти с нулём! UPDATE Да, проверил в Delphi, действительно, присвоение указателю динамического массива nil освобождает занимаемую массивом память! Так что, в этом данном месте исходного кода ничего не должно приводить к утечками памяти.. evg_m, согласен. +1 Последний раз редактировалось Serge_Bliznykov; 25.02.2013 в 14:36. |
|
25.02.2013, 15:00 | #10 | |
Пользователь
Регистрация: 23.04.2011
Сообщений: 42
|
Цитата:
Правильно ли я понимаю, что Вы предлагаете выполнять операцию BaseStream.Read(BinPoints, SizeOf(SizeBinPoints)) столько раз, сколько вообще записей в файле? Или я не правильно Вас понял? Вообще даже чтение по 10 лямов никак не влияет - я даже размер объявляю единожды - сразу максимум даю и все. Весь ступор происходит при заполнении Dictionary - просто я сейчас как наблюдаю ошибку: читаю по миллиону, в памяти сразу отделяется кусок под файл - оперативка под 813 000 Кб (сам файл 780 Мб), начинается счет, на 7-ом миллионе выдается ошибка и в памяти остается 242 344 Кб, что как раз соответствует немногим более 7 млн. записей (примерно 7 млн. 300 тысяч) - т.е. все это именно в Dictionary и именно из-за нее выдается ошибка ибо просто чтение без каких либо операций никаких ошибок не выдает. Ну по крайней мере я так думаю и понимаю. Последний раз редактировалось Freimaks; 25.02.2013 в 17:40. |
|
|
Похожие темы | ||||
Тема | Автор | Раздел | Ответов | Последнее сообщение |
Load exe into memory and run it from memory | artush1984 | Win Api | 10 | 06.02.2012 18:43 |
Правильная работа с формами | CodeNOT | PHP | 5 | 12.04.2011 12:34 |
Правильная работа скрола в панели. | evilgeniuz | Общие вопросы .NET | 0 | 29.09.2010 00:17 |
Правильная работа условия if | Andruha10 | PHP | 1 | 22.08.2010 21:23 |
Не правильная работа for .. to | Neptunium | Общие вопросы Delphi | 7 | 05.04.2010 00:32 |