![]() |
| ||
|
|
Новости |
Поиск |
FAQ |
Статьи |
Книги |
Новости VCL
| | Форумы ЧАТ |
Орешник |
|
| |||
| |||
« предыдущая ветвь | форум | следующая ветвь »
Использование общих переменных в различных потоках [D7, WinXP]
tipman © (2008-12-22 16:42:00)Есть массив. Объявлен глобально. Один поток загружает массив, другой потихоньку параллельно данные выуживает из него. Могут ли быть проблемы в данном случае, например, при одновременной попытке записать и считать данные разными потоками. И если да, то подскажите пожалуйста как это дело разрулить.
Спасибо
zulus5 (2008-12-24 00:44:00) [1]я использую D7
DVM (2008-12-23 23:16:00) [2]
> zulus5 © (23.12.08 21:53) [8]
> ALocker: TMultiReadExclusiveWriteSynchronizer;
Хочу заметить, что TMREWS в D6 имеет ошибку, приводящуюю к взаимоблокировке потоков, поэтому использовать его можно только в более новых версиях делфи. Производительность приложения с TMREWS иногда в разы хуже, чем с критическими секциями, но есть и ситуации, где можно получить хороший выигрыш.
zulus5 (2008-12-23 21:53:00) [3]Конечно могут!!!!
Я использую такую конструкцию... очень помагает!!!
Здесь важно ALocker - это и есть решение твоей проблемы!!!
Класс от СМО с очередями где происходит передача данных от одного класса до другого в потоках! Скорость УУУх!!! 100000 - 200000 файлов за 24-30 минут по дереву обработки или сценарию.
// класс потока
Type
TTextOrSign = class (TBaseClass) // наследуем класс от базового класса
private
....
ALocker: TMultiReadExclusiveWriteSynchronizer;
....
constructor TTextOrSign.Create;
begin
Inherited Create;
Try
Bitmap:= TBitMap.Create;
Bitmap.LoadFromResourceName( HInstance, 'BITMAP_WEBTEXT' );
Except end;
ALocker:= TMultiReadExclusiveWriteSynchronizer.Create;
end;
Destructor TTextOrSign.Destroy;
begin
if fStarted then Stop();
ALocker.Free;
inherited Destroy;
end;
Function TTextOrSign.SendData( iWorkData: PWorkData; frComp:Pointer):boolean;
Var FileN, err: String;
begin
ALocker.BeginWrite;
if Self.fWorkData^.Data = nil then GetMem(Self.fWorkData^.Data, fiData.MaxBuffSize);
Result:= False;
// проверка на запуск
If Self.fStarted=False Then Exit;
Try
If SozdavatPotok=True then
begin
If TekuchixPotokov<MaxPotokov Then
Begin
if iWorkData^.Size > (fiData.MaxBuffSize) then
begin
err:= 'Размер данных превышает размер буфера! (BaseClass.SendData)';
Windows.SendMessage(fiData.MessList.WinHndl, fiData.MessList.Error, Integer(Self), Integer(err));
end
else
Begin
MoveMemory( Self.fWorkDAta^.Data, iWorkData^.Data, iWorkData^.Size);
FileN:= PString( Self.fWorkData^.Data )^;
Inc(TekuchixPotokov);
FRemMulti:= TExecuteThreadTXT.Create(
PBaseClass(Self), FileN, DirStat,
VestiStatistiku, PerSoob, ZagZenit, Procent,
DopuskNull, Glubina_analiza, DlinaZag, ProcentProbelov );
FRemMulti.Resume;
Result:= True;
Windows.SendMessage(fiData.MessList.WinHndl, fiData.MessList.Send, Integer(Self), Integer(frComp));
Sleep(0);
end;
end;
end
else
begin
If inherited SendData(iWorkData, frComp) then
Begin
FileN:= PString( fWorkData^.Data )^;
FileTXT( FileN, Glubina_analiza );
Result:= True;
end;
end;
Except
Result:= False;
end;
ALocker.EndWrite;
end;
tipman (2008-12-23 20:57:00) [4]type
TMy = record
X1: integer;
X2: integer;
X3: integer;
Y1: Double;//cardinal;
Y2: Double;//cardinal;
Y3: Double;//cardinal;
Y4: Double;//cardinal;
Y5: Double;
end;
TMyMy = record
count: integer;
data: array of TMy;
end;
............
var
MyMy: TMyMy;
вот со структуркой MyMy типа TMyMy и надо работать параллельно в 2-х, 3-х потоках....
Вообщем то уже реализовал через критические секции, пробовал без них действительно ексесс виолайшн был :)
Johnmen (2008-12-23 20:36:00) [5]
> tipman (22.12.08 16:42)
Массив чего? И какова единица "данных"?
Sha (2008-12-23 10:08:00) [6]
> критические секции самое то
есть еще lock-free техники (см. memory barrier)
tipman (2008-12-22 20:39:00) [7]Synchronize, судя по Стиву Тейксейра, синхронизирует вторичный поток с основным и служит в основном для работы с окнами, т.е. с визуальными компонентами. Механизм его ясен и это не то. Мне нужно синхронизировать вторичные потоки, и критические секции самое то...
Всем очень благодарен.
Leonid Troyanovsky (2008-12-22 17:51:00) [8]
> tipman (22.12.08 16:42)
> да, то подскажите пожалуйста как это дело разрулить.
TThread.Synchronize, RTFM.
--
Regards, LVT.
Palladin (2008-12-22 16:50:00) [9]
> Могут ли быть проблемы в данном случае,
Запросто.
> И если да, то подскажите пожалуйста как это дело разрулить.
Способов очень много и они достаточно подробно описаны у Рихтера.
Самый простой - критические секции (TCriticalSection)
Сергей М. (2008-12-22 16:47:00) [10]
> Могут ли быть проблемы в данном случае,
Могут.
> как это дело разрулить
Защитить операции записи и чтения критической секцией.
см. класс TCriticalSection
пример:
cs.Enter; //захват секции
try
.. любая операция с защищаемым ресурсом, в д.с. с глоб.массивом ..
finally
cs.Leave; //освобождение секции
end;