Форум: "Основная";
Текущий архив: 2003.10.02;
Скачать: [xml.tar.bz2];
ВнизCOM + потоки Найти похожие ветки
← →
Sunny (2003-09-19 13:56) [0]Добрый вечер Всем!
Помогите разобраться с потоками. По сути работаю с ними первые.
Есть клиент серверное приложение.
Клиент помимо всего прочего осуществляет вывод ряда отчетов в эксель. Процесс формирования отчетов достаточно долгий, потому решила сунуть их в отдельные потоки.
Вот код на сей момент:
unit Thread_Tabel;
interface
uses
Classes, Dialogs, SysUtils, Variants
, ActiveX // без этого не воспринимает CoInitilize/CoUnitilize
, ComObj;
type
TMyThread = class (TThread)
protected
WorkBook,Excel,Ws: OleVariant;
procedure Execute; override;
// function CoInitialize(pvReserved: Pointer): HResult; stdcall;
// procedure CoUninitialize; stdcall;
public
{ Public declarations }
constructor create;
procedure BlockMenu;
end;
Var
thTabel: TMyThread;
implementation
uses main, DM;
procedure TMyThread.Execute;
var
...
begin
//вызов отчета
Synchronize(BlockMenu);
CoInitialize(nil);
Excel := CreateOleObject("Excel.Application");
Excel.DisplayAlerts := false;
try
WorkBook := Excel.Workbooks.add(g+"\Шаблоны\Табель.xls");
...
Excel.Visible := True;
Except
MessageDlg("Перенос данных не удался.", mtInformation, [mbOk], 0);
excel.displayalerts := false;
Synchronize(BlockMenu);
excel := null;
ws := null;
if fDM.qTabel.Active then
fDM.qTabel.close;
CoUninitialize;
end;
Synchronize(BlockMenu);
excel := null;
ws := null;
if fDM.qTabel.Active then
fDM.qTabel.close;
CoUninitialize;
end;
procedure TmyThread.BlockMenu;
begin
... //блокирует меню
end;
constructor TMyThread.Create;
begin
inherited Create(False);
end;
end.
Вопросы:
1) правильно ли для каждого потока заводить отдельный модуль потока? Пробовла в одном модуле описать с помощью case, но ничего хорошего не вышло
2) как правильно вызывать CoInitilize/CoUnitilize, так чтобы не пришлось грузить ActiveX
3) надо ли после CoUnitilize, вызывать еще и thTabel.Free, хотя тода поток у меня остается висеть
Извините если вопросы глупые. Заранее благодарна за ответы.
← →
Владислав (2003-09-19 14:17) [1]1) правильно ли для каждого потока заводить отдельный модуль потока? Пробовла в одном модуле описать с помощью case, но ничего хорошего не вышло
Ни фига не понял :-/???
2) как правильно вызывать CoInitilize/CoUnitilize, так чтобы не пришлось грузить ActiveX
Ну типа, объявить.
function CoInitializeEx; external ole32 name "CoInitializeEx";
← →
Sunny (2003-09-19 14:28) [2]Владислав>
Приведен код модуля потока для отчета "Табель"
Есть еще ряд отчетов, которые на данный момент выполняются в основном потоке.
Так вот для каждого из них необходимо заводить отдельный модуль или не обязательно?
← →
Master (2003-09-19 14:43) [3]Ты хочеш для каждого отчета заводить отдельный поток или все через один пото выполнять? Думаю, что пул тредов тебе ненужен. Выполняй все через они поток. Внутри execute сделай цикл который выполняется where not Terminated и после этого CoUninitialize. Чтобы выполнилось наверника Try finally.
В нутри цикла будеш брать новое задание и выполнять пока незакончится список отчетов.
P.S.
Если захоч, чтобы все красиво было воспользуйся WaitForMultipleObjects я такую конструкцию придумал
TActivEvent = (actCmd, actExit);
MObject = record
Event: array[TActivEvent] of THandle;
end;
tmEvent: MObject;
Status := WaitForMultipleObjects(Ord(High(tmEvent.Event)) + 1,@tmEvent.Event, false, INFINITE);
case TActivEvent(Status) of
actExit: Terminate;
actCmd: FetchArray;
else
if Status = WAIT_TIMEOUT then
GetServerIP;
end;
Страницы: 1 вся ветка
Форум: "Основная";
Текущий архив: 2003.10.02;
Скачать: [xml.tar.bz2];
Память: 0.45 MB
Время: 0.009 c