Форум программистов, компьютерный форум, киберфорум
Наши страницы
C# для начинающих
Войти
Регистрация
Восстановить пароль
 
Рейтинг 4.56/16: Рейтинг темы: голосов - 16, средняя оценка - 4.56
Mans7
59 / 59 / 14
Регистрация: 05.08.2011
Сообщений: 323
Записей в блоге: 5
#1

Освобождение памяти в потоках

03.01.2012, 13:07. Просмотров 2986. Ответов 8
Метки нет (Все метки)

Доброго времени суток. Помогите пожалуйста, товарищи программисты. Приложение может создавать от 1 до N параллельных одновременно работающих потоков (стандартно до 10-15) по ОДНОМУ НАПРАВЛЕНИЮ. "Одно направление" - это тоже поток. Направлений до 10. То есть я имею порядка 10 потоков, внутри каждого из которых создаётся ещё масса потоков, но что бы не убить систему сразу, используется пул потоков, который контролирует максимально возможное кол-во работающих потоков одновременно. Проблема в том, что по задумке внутренние потоки создаются, и, доходя до своего логического конца, самоуничтожаются (так я думаю), но беда в том, что объём используемой оперативной памяти, не смотря на это, только растёт, и растёт довольно быстро. Так вскоре забивается вся оперативная память (6 гб) и я даже не знаю что и делать... Такое впечатление, что потоки после завершения работы, используемые ресурсы не удаляют за собой (либо сборщик мусора не делает этого).

Как бы то ни было, потоки создаются и успешно завершаются в пуле, но память продолжает забиваться и забиваться, без освобождения... Помогите пожалуйста, что с этим можно сделать?
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
Similar
Эксперт
41792 / 34177 / 6122
Регистрация: 12.04.2006
Сообщений: 57,940
03.01.2012, 13:07
Ответы с готовыми решениями:

Освобождение памяти
Подскажите, пожалуйста, я ещё зелёный в C#. Есть у меня класс Form1, при...

Выделение/освобождение памяти
помогите пожалуйста, в С++ есть конструкции вида xx=AllocMemInt2D(LL, NN);...

Выделение и освобождение памяти
Здравствуйте, помогите пожалуйста разобраться. Скажите является ли следующий...

Освобождение памяти объекта подписанного на событие
Народ, я тут натолкнулся на такой случай который меня озадачил. Изначально я...

Освобождение памяти при удалении элемента в List<T>
Доброго времени суток, уважаемые форумчане! Скажите пожалуйста, если...

8
kolorotur
Эксперт .NET
10201 / 8560 / 2111
Регистрация: 17.09.2011
Сообщений: 14,698
Завершенные тесты: 1
03.01.2012, 13:21 #2
Дело, скорее всего, не в потоках, а в том, что вы где-то храните ссылки на создаваемые объекты, которые потом не выходят из области видимости, в результате чего сборщик их не подчищает.

Покажите код - будет намного проще разобраться в проблеме.
0
Mans7
59 / 59 / 14
Регистрация: 05.08.2011
Сообщений: 323
Записей в блоге: 5
03.01.2012, 13:44  [ТС] #3
Код большой, и я боюсь, что вы не разберётесь, я ещё не везде комменты поставил... Вот, попробуйте пожалуйста: KataLOG.rar (не знаю как правильно прикручивать файлы, сделал так)
0
Mans7
59 / 59 / 14
Регистрация: 05.08.2011
Сообщений: 323
Записей в блоге: 5
03.01.2012, 13:59  [ТС] #4
Смысл программы такой:
1. "заходит" на сайт интернет-магазина, списывает "каталоги" в checklistbox1 и предлагает пользователю выбрать, какие необходимы каталоги. После выбора работа продолжается с выделенными каталогами.
2. на каждый каталог создаётся поток в котором:
2.1. заходит на страничку каталога, находит товар на странице. Нашел - отправляет ссылку на этот товар в ещё один новый поток:
2.1.1. этот поток находит всю необходимую инф-ю и добавляет её в БД
2.2. ищет ещё товары, которых обычно ооочень много

p.s. пул потоков реализован вручную (знаю что очень некрасиво и некачественно, но дело не в нём).
0
kolorotur
Эксперт .NET
10201 / 8560 / 2111
Регистрация: 17.09.2011
Сообщений: 14,698
Завершенные тесты: 1
04.01.2012, 10:47 #5
Цитата Сообщение от Mans7 Посмотреть сообщение
Код большой, и я боюсь, что вы не разберётесь
Да не смешите. 600 строк - это уровень чуть выше "Hello world".

Я не буду комментировать организацию и синхронизацию (точнее, ее отсутствие) потоков - вы ее сами хорошо описали в своем последнем сообщении, но вот что сразу же бросается в глаза - это создание кучи соединений с БД и веб-клиентов, ресурсы которых не освобождаются должным образом через вызов методоа Dispose.
Например:
C#
1
2
WebClient wc3 = new WebClient();
WEBtext3 = wc3.DownloadString(sTovarURL);
надо бы сделать так:
C#
1
2
using (WebClient wc3 = new WebClient())
   WEBtext3 = wc3.DownloadString(sTovarURL);
Я с API под VistaDB не работал, но у меня сильнейшие подозрения, что там делать надо точно так же:
C#
1
2
3
4
5
6
7
8
9
10
using (VistaDBCommand SQLThreadCommand = MyConnection.CreateCommand())
{
   SQLThreadCommand.CommandText = "INSERT INTO Katalogs (KatalogName, KatalogURL) ";
   SQLThreadCommand.CommandText += "VALUES (@KN,@KURL)";
   SQLThreadCommand.Parameters.Add("@KN", VistaDB.VistaDBType.Text);
   SQLThreadCommand.Parameters[0].Value = sKatalogName;
   SQLThreadCommand.Parameters.Add("@KURL", VistaDB.VistaDBType.Text);
   SQLThreadCommand.Parameters[1].Value = sKatalogURL;
   SQLThreadCommand.ExecuteNonQuery();
}
Сделайте должное освобождение ресурсов во всех местах, где используется WebClient и работа с базой и попробуйте протестить снова.

Возможно, в коде имеются еще скрытые утечки, связанные с "потерянными" потоками. Это легко проверить, включив в диспетчере задач колонку "Threads" и наблюдая за количеством потоков.
Если оно постепенно растет, значит какой-то поток не завершается или теряется.
1
Mans7
59 / 59 / 14
Регистрация: 05.08.2011
Сообщений: 323
Записей в блоге: 5
04.01.2012, 13:31  [ТС] #6
Сделал как Вы порекомендовали, но память как росла вверх неумолимо, так и растёт... Возможно лишь теперь не так быстро, но толку от этого мало =(...

Добавлено через 18 минут
Судя по монитору процессов, количество потоков достигает некоторого значения (при двух направлениях 21-29) и не превышает его. То есть процессы успешно закрываются, но, память не освобождается.

Попытался внести GC.Collect() - не помогает.
0
kolorotur
Эксперт .NET
10201 / 8560 / 2111
Регистрация: 17.09.2011
Сообщений: 14,698
Завершенные тесты: 1
04.01.2012, 13:32 #7
Прицепите код с внесенными изменениями - будем смотреть что дальше.
0
Mans7
59 / 59 / 14
Регистрация: 05.08.2011
Сообщений: 323
Записей в блоге: 5
04.01.2012, 13:40  [ТС] #8
Что-то мне подсказывает что придется всю программу с нуля делать заного и теперь уже что-то новое учитывать... в данном случае - память... уже 4-й или 5-й раз будет, сбился со счета...

Попробовал использовать Dispose на объекты классов типа Webclient - безрезультатно.
0
Вложения
Тип файла: rar KataLOG.rar (5.5 Кб, 18 просмотров)
Mans7
59 / 59 / 14
Регистрация: 05.08.2011
Сообщений: 323
Записей в блоге: 5
04.01.2012, 14:41  [ТС] #9
Нашел интересную информацию:
http://www.gotdotnet.ru/forums/2/124760/588405/#post588405

Добавил себе
C#
1
2
3
4
using System.Runtime.InteropServices;
  [ DllImport( "kernel32.dll" ) ]
  public static extern bool SetProcessWorkingSetSize( IntPtr handle,
int minimumWorkingSetSize, int maximumWorkingSetSize );
И вставил в начало fThreadTov
C#
1
SetProcessWorkingSetSize( System.Diagnostics.Process.GetCurrentProcess().Handle,-1, -1 );
И вижу следующие изменения - программа так же притормаживает (это терпимо), а вот память плавно доходит до 20-30, потом падает до 5-10, доходит до 50, падает до 10-15, в общем за несколько минут работы, потребляемая память в среднем держится на 10-30. Все цифры в мегабайтах.

Хотя, как утверждает диспетчер задач, приложение кушает 50% ЦП. Система работает без изменений... Интересно - проблема решена? =)

Добавлено через 11 минут
До сих пор программулина работает в штатном режиме =) то есть всё достаточно стабильно держится и добавлено более 450 товаров в бд при обработке пока что одного только направления в котором 5-6 потоков. То есть суммарно приложение делает 7-8 потоков (1 основной главный поток, 1 первый параллельный на направление, 5-6 на товары направления). Все показатели без изменений. Вроде здорово.

Добавлено через 37 минут
Не знаю, будет ли продолжение темы, но, тем не менее, СПАСИБО большое, kolorotur, за помощь!
1
04.01.2012, 14:41
MoreAnswers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
04.01.2012, 14:41

Освобождение памяти от переменных (или динамические переменные)
Здравствуйте! Подскажите пожалуйста одну такую деталь: Вот в C/C++, мы...

Освобождение памяти
Есть форма, из которой вызывается дочерняя форма, на дочерней форме есть...

Освобождение оперативной памяти при использовании Awesomium
Всем привет! Работаю с Awesomium, и всё было хорошо, пока я не открыл...


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

Или воспользуйтесь поиском по форуму:
9
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2018, vBulletin Solutions, Inc.
Рейтинг@Mail.ru