Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > Delphi программирование > Работа с сетью в Delphi
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 30.03.2015, 17:22   #1
tromani
Пользователь
 
Регистрация: 10.12.2010
Сообщений: 23
По умолчанию многопоточность indy и ошибки

Всем привет, кто знает помогите разобраться

суть проблемы такова:

есть простой поток:
Код:
 
procedure TParseTH.Execute;
var
  idHTTP_RP:TidHTTP;
  idCCM:TIdCookieManager;
begin
  FreeOnTerminate:=True;
  OnTerminate:=fmMain.ThreadDone;
  idCCM:=TIdCookieManager.Create();
  idHTTP_RP:=TIdHTTP.Create();
  idHTTP_RP.CookieManager:=idCCM;
  try
   idHTTP_RP.Get('something');
  except
  end;
  try idHTTP_RP.Disconnect except end;
  idHTTP_RP.Free;
  idCCM.Free;
end;
ThreadDone просто счетчик завершенных потоков

и есть некий цикл их (потоки генерирующий)
Код:
    thFinished:=0; //счетчик завершенных потоков
    thCount:=0;// счетчик запущенных
    repeat
      if thCount<upDown2.Position then
      begin
        try
          with TParseTH.Create() do;
          Inc(thCount);
        except
        end;
      end;      
      Sleep(400);
      ProgressBar1.Position:=thFinished;
      Application.ProcessMessages;
    until (needEx);

    while thCount<>0 do
    begin
      Sleep(300);
      ProgressBar1.Position:=thFinished;
      Application.ProcessMessages;
    end;
все в общем-то более-менее сносно работает при условии 15-20 запущенных потоков,
НО если убрать строчку Sleep(400); и ограничить число потоков до 100 например то вылетает 10053
если счетчик потоков ограничить 50-60 при наличии Sleep(400) то переодически внутри какоголибо потока имеем коннекшн тайм-аут...

т.е. вопрос по сути я сильно много-го хочу и 100 потоков это уже органичение по нагрузку на сеть или я чтото таки делаю не так?

Последний раз редактировалось Stilet; 30.03.2015 в 17:25.
tromani вне форума Ответить с цитированием
Старый 30.03.2015, 17:27   #2
Stilet
Белик Виталий :)
Старожил
 
Аватар для Stilet
 
Регистрация: 23.07.2007
Сообщений: 57,097
По умолчанию

Цитата:
то вылетает 10053
Может тебя сервер отрезает, понимая что твой бот стучится и подозревая какую-то атаку?
А что программа то делать должна? Какова задача?
I'm learning to live...
Stilet вне форума Ответить с цитированием
Старый 30.03.2015, 17:33   #3
lomastr_
Форумчанин
 
Регистрация: 16.01.2015
Сообщений: 672
По умолчанию

что-то странный код, зачем эти слипы?
таймаут это нормально
это
Цитата:
OnTerminate:=fmMain.ThreadDone;
и это
Цитата:
while thCount<>0 do
begin
Sleep(300);
ProgressBar1.Position:=thFinished;
Application.ProcessMessages;
end;
плохо

Цитата:
вопрос по сути я сильно много-го хочу и 100 потоков это уже органичение по нагрузку на сеть или я чтото таки делаю не так?
не страшно 100 как страшно что канал убиваете

Последний раз редактировалось Stilet; 30.03.2015 в 18:47.
lomastr_ вне форума Ответить с цитированием
Старый 30.03.2015, 17:41   #4
tromani
Пользователь
 
Регистрация: 10.12.2010
Сообщений: 23
По умолчанию

Цитата:
что-то странный код, зачем эти слипы?
ну говорю без слипов сразу 10053 вылетает
Цитата:
while thCount<>0 do
begin
Sleep(300);
ProgressBar1.Position:=thFinished;
Application.ProcessMessages;
end;
это плохо
ну это вообще по сути к проблеме не относится чем плохо я не знаю

Цитата:
не страшно 100 как страшно что канал убиваете
не могли б вы поподробнее пояснить что имеете ввиду

Последний раз редактировалось tromani; 30.03.2015 в 17:46.
tromani вне форума Ответить с цитированием
Старый 30.03.2015, 17:47   #5
lomastr_
Форумчанин
 
Регистрация: 16.01.2015
Сообщений: 672
По умолчанию

слип вам помогает при
Цитата:
15-20 запущенных потоков
далее он уже не чем не поможет
Цитата:
ну это вообще по сути к проблеме не относится чем плохо я не знаю
плохо то что оно так не делается, вы перегружаете главный поток
lomastr_ вне форума Ответить с цитированием
Старый 30.03.2015, 17:59   #6
tromani
Пользователь
 
Регистрация: 10.12.2010
Сообщений: 23
По умолчанию

Цитата:
Сообщение от lomastr_ Посмотреть сообщение
плохо то что оно так не делается, вы перегружаете главный поток
а не подскажите как оно должно правильно делаться
или вы имеете ввиду что я перегружаю главный поток вот этим:
Код:
while thCount<>0 do
begin
Sleep(300);
ProgressBar1.Position:=thFinished;
Application.ProcessMessages;
end;
если вы это имеете ввиду то не обращайте внимания оно ж уже стоит после основного запуска всех нужных потоков да и в это время все равно ничего в главном не должно происходить оно должно просто подождать пока все запущенные потоки завершаться

проблема в том что из-за большого количества запущенных потоков вылетает коннектион тайм-аут ВНУТРИ созданного потока а не в главном или 10053

Последний раз редактировалось Stilet; 30.03.2015 в 18:48.
tromani вне форума Ответить с цитированием
Старый 30.03.2015, 18:26   #7
lomastr_
Форумчанин
 
Регистрация: 16.01.2015
Сообщений: 672
По умолчанию

дело не в потоках, а в том что что вы сразу нагружаете инет сильно, слип вам дает небольшую задержку, но это спасает только когда мало, при большом количестве канал "ложится", т.е. вот вам и таймауты, упираетесь в железо так сказать
Цитата:
а не подскажите как оно должно правильно делаться
доп. поток должен по завершении сам сигнализировать (или сообщение (PostMessage) кидать или синхронизировать) о статусе, и циклов никаких не надо

стартуйте 10 к примеру, потом один отработал следующий запускаете и так далее, пока все не отработают

если делфи из новых возьмите какой готовый пул

Последний раз редактировалось Stilet; 30.03.2015 в 19:51.
lomastr_ вне форума Ответить с цитированием
Старый 30.03.2015, 20:05   #8
tromani
Пользователь
 
Регистрация: 10.12.2010
Сообщений: 23
По умолчанию

Цитата:
Сообщение от lomastr_ Посмотреть сообщение
дело не в потоках, а в том что что вы сразу нагружаете инет сильно, слип вам дает небольшую задержку
ага, вот это собственно я и хочу понять
а не подскажите, есть ли способ понять так сказать возможности канала перед очередным запуском потока например.... или тут только увеличить продолжительность слипа реально делу поможет
tromani вне форума Ответить с цитированием
Старый 30.03.2015, 20:16   #9
lomastr_
Форумчанин
 
Регистрация: 16.01.2015
Сообщений: 672
По умолчанию

необходимость использования в программе слипа почти равна 0, за очень редким исключением
сами подумайте толку от него? ну вот вы поставите больше и что? тогда простои начнутся а прога будет "висеть"... кому она такая нужна?
я же вам сказал несколько вариантом, что не устраивает?
lomastr_ вне форума Ответить с цитированием
Старый 30.03.2015, 23:53   #10
tromani
Пользователь
 
Регистрация: 10.12.2010
Сообщений: 23
По умолчанию

помоему вы код в код не очень вникли...
еще раз
мне надо в общей куче выполнить 2000-3000 запросов однотипных, последовательно ждать долго
Код:
procedure TfmMain.ThreadDone(Sender:TObject);
begin
  Inc(thFinished);
  Dec(thCount);
end;
тут описана событие на OnTerminate потока

Код:
OnTerminate:=fmMain.ThreadDone;
этот кусок из основного приложения или основного потока как угодно (кусок который меня интересует все остальное неважно):
Код:
thFinished:=0; //счетчик завершенных потоков
thCount:=0;// счетчик запущенных
   
  repeat
      if thCount<upDown2.Position then // если число запущенных в данный момент потоков меньше определенного значения , 
    //то запускаем новый поток
      begin
        try
          with TParseTH.Create() do;
          Inc(thCount);
        except
        end;
      end;      
      Sleep(400); //если число потоков в данный момент равно максимально заданному основной поток ждет ему 
   //собственно больше ничего делать не надо просто дождаться завершения всех потоков
      ProgressBar1.Position:=thFinished;
      Application.ProcessMessages;
    until (needEx);
вопрос мой собственно звучал чем так если я ограничиваю количество одновременно запущенных потоков 50-60 получается так что некоторые завершаются коннектиеон тайм аут т.е. очевидно что их слишком много и либо сеть либо железо не справляется, т.е. вопрос: есть ли какойто очевидный способ понять состояние нагруженности канала и прочего для принятия программой решения запускать ли очередной поток или стоит подождать завершения предыдуще запущенных, я не спрашивал про адекватность применения Sleep и так далее
да и слип тут оправдан ибо если я просто буду создавать подряд 100 потоков то либо получу 10053 либо уже от сайта к которому обращаюсь коннекшин резет бай пир или клосед грэсфули

Последний раз редактировалось Stilet; 31.03.2015 в 06:35.
tromani вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Многопоточность Indy niva622 Общие вопросы Delphi 11 25.05.2013 19:22
[Indy]Отловить ошибки возникающие при работе с проксями bakanaev Общие вопросы Delphi 8 05.12.2012 20:48
INDY. Ошибки Кодировщика и Декодировщика Vol666 Работа с сетью в Delphi 9 04.09.2009 08:15
Многопоточность Indy AVer Работа с сетью в Delphi 14 14.02.2009 22:10
Многопоточность с INDY Ragnarek Работа с сетью в Delphi 2 27.01.2009 13:25