Есть ListBox куда записываются из разных точек типа логи. Выполняется прога - и пишет, пишет. Так отладка, визуализация. Но иногда требуется это записать в файл.
Написал:
procedure TForm1.ListBox1Add(S: string);
var nf: string;
begin
if ListBox1.Items.Count>1000 then
ListBox1.Items.Delete(ListBox1.Items.Count-1);
ListBox1.Items.Insert(0,DateTimeToStr(Now)+': '+S);
logcount:=logcount+1;
//записать в файл логов, проверив 1 на дату
if logcount mod 1000 =0 then
try
nf:=datetimetostr(Now)+'.log';
while (pos(':',nf)>0) do
nf[pos(':',nf)]:='_';
nf:=Form2.DirectoryEdit1.Text+'/'+nf;
listbox1.Items.SaveToFile(nf);
except
showmessage(inttostr(logcount)+' Херово!!!');
end;
end;
Вроде все работает. Но когда пришлось вставить нагрузочное тестирование, оказалось, что в блоке записи в файл - что-то происходит. Доходило до того, что прога просто из памяти вываливалась.
Чую, что это из-за того, что либо 2 процесса одновременно пытаются в файл писать, либо пишется в файл строка бокса, которую уже прибил.
Что лучше и как использовать для такого случая?
Записать логи в файл
Модераторы: Duncon, Naeel Maqsudov, Игорь Акопян, Хыиуду
- Naeel Maqsudov
- Сообщения: 2570
- Зарегистрирован: 20 фев 2004, 19:17
- Откуда: Moscow, Russia
- Контактная информация:
А запись строчек в лог и сохранение в файл делаются из разных тредов?
Синхронизацию надо использовать.
Надо создавать объект синхронизации (CriticalSection) (в момент инициализации того модуля с которым ассоциирована форма с listbox-ом)
В этом же модуле определить два метода
AddStringToLog и FlashToFile (кстати, FlashToFile можно делать непосредственно в момент добавления записи (т.е. внутри AddStringToLog) и обеспечить механизм "ротации" логов).
Все кто пишет логи должны пользоваться процедурой AddStringToLog!
Все операции со списком (добавление/удаление/сохранение в файл) поместить в операторные скобки
Синхронизацию надо использовать.
Надо создавать объект синхронизации (CriticalSection) (в момент инициализации того модуля с которым ассоциирована форма с listbox-ом)
В этом же модуле определить два метода
AddStringToLog и FlashToFile (кстати, FlashToFile можно делать непосредственно в момент добавления записи (т.е. внутри AddStringToLog) и обеспечить механизм "ротации" логов).
Все кто пишет логи должны пользоваться процедурой AddStringToLog!
Все операции со списком (добавление/удаление/сохранение в файл) поместить в операторные скобки
Код: Выделить всё
EnterCriticalSection(XXX);
try
//bla-bla-bla
finnally
LeaveCriticalSection(XXX);
end;
Да, запись идет из разных потоков, как из головного модуля, так и из создаваемых потоков динамически.
Сенкс. Бум думать.
Сенкс. Бум думать.