|
 |
На сайте
Статьи
Софт
|
|
|
|
|
|
|
Первые шаги с TThread в Delphi
Карих Николай, Мастера Delphi
Вне зависимости от того, хотим мы этого или нет, но прогресс движется
дальше, появляются все новые технологии, новые процессоры, новые "высоты"
производительности. В связи с этим, все чаще программистам приходится
разрабатывать программы, которые используют сложные операции, в которых
важна скорость и которые выполнялись бы одновременно с другими. Этому
вопросу как раз и посвящена данная статья - создание многопоточных
приложений (со множеством дочерних процессов, которые выполняются
одновременно).
Итак, зачем же нужен класс Thread и его потомки? Во-первых, этот
объект позволяет создавать как бы несколько программ в одной
(несколько процессов, или, потоков). Во-вторых, эти процессы
могут выполняться как по очереди, так и одновременно (как
запрограммирует разработчик). В-третьих, из этих процессов
можно легко получить доступ ко всем глобальным данным программы,
т.к. класс процесса является, по сути, просто частью программы -
обычным юнитом (unit). В-четвертых, можно создать своих собственных
потомков TThread и запустить сразу несколько экземпляров одного и
того же созданного класса. В-пятых, каждым процессом очень легко
управлять - запускать, завершать, приостанавливать, прерывать,
устанавливать приоритетность, и т.д.
Итак, рассмотрим некоторые свойства, методы и события класса TThread.
| Свойства |
|
Методы |
|
События
|
|
FreeOnTerminate - освобождать ли
память, выделенную под экземпляр класса процесса, когда
этот процесс завершается. Если True - при завершении
процесса (или при вызове метода Terminate) экземпляр
класса автоматически освобождается (аналогично вызову метода
Free).
Тип: Boolean;
Handle (ThreadID) - дескриптор процесса.
Эта величина может быть использована для управления процессом
через функции WinAPI.
Тип: THandle;
ReturnValue - возвращаемое
значение при завершении процесса.
Тип: Integer;
Priority - приоритет процесса.
Возможные значения этого свойства мы разберем немного позже.
Тип: TThreadPriority;
Suspended - показывает, в
каком состоянии находится процесс: True - приостановлен,
False - в нормальном.
Тип: Boolean;
Terminated - показывает,
завершен ли процесс. True - завершен, False - нет.
Тип: Boolean;
|
|
Create(CreateSuspended: Boolean) -
создает экземпляр класса. Параметр CreateSuspended
указывает на то, нужно ли создавать приостановленную задачу
(True), или запускать ее сразу (False);
Suspend - приостанавливает
выполнение процесса;
Resume - продолжает
выполнение процесса после Suspend;
Terminate - полностью
прекращает выполнение процесса;
WaitFor - ждет завершения
процесса, возвращая затем код его завершения (ReturnValue);
Synchronize(Method: TThreadMethod)
- синхронизирует выполнение метода процесса, позволяя ему
работать параллельно с другими процессами.
|
|
OnTerminate - возникает, когда
процесс находится в стадии завершения.
|
Итак, что же такое приоритет? Приоритет - это величина, определяющая,
насколько данный процесс должен выполнятся быстрее по сравнению с другими.
Т.е., другими словами, чем выше приоритет процесса, тем больше времени
он отбирает у системы и других, параллельно работающих процессов. Далее
разберем возможные значения свойства Priority класса TThread в порядке
возрастания приоритета:
- tpIdle - процесс выполняется только тогда, когда система
не занята и больше нет работающих в данных момент процессов;
- tpLowest - на два пункта ниже нормального;
- tpLower - на один пункт ниже нормального;
- tpNormal - нормальный. Такой приоритет у большинства задач;
- tpHigher - на один пункт выше нормального;
- tpHighest - на два пункта выше нормального;
- tpTimeCritical - самый высокий приоритет - занимает все
время процессора и системы. Это приоритет для систем реального времени,
для которых важна каждая секунда и даже малейшая задержка может привести
к сбою. Будьте осторожны с этим приоритетом!
Приведем небольшой пример того, как можно создать отдельный процесс:
|
|
{Определение класса TMyThread}
type
TMyThread = class(TThread)
private
{ Private declarations }
protected
procedure DoWork;
procedure Execute; override;
end;
implementation
procedure TMyThread.Execute;
begin
{Если Вы хотите, чтобы процедура DoWork выполнялась лишь один раз - удалите цикл while}
while not Terminated do
Synchronize(DoWork);
end;
procedure TMyThread.DoWork;
begin
{Здесь можно уже выполнять те задачи, которые должны быть исполнены процессом}
end;
|
А теперь - замечательный пример для изучения Thread! В нижеследующем примере
приложение создает два параллельно работающих процесса. Один Thread
пытается установить флажок CheckBox1 в положение "включено" (Checked := True),
а другой, передергивая первого - в "выключено".
|
|
{В форму Form1 нужно поместить TCheckBox - CheckBox1
и одну кнопку TButton - Button1}
{Определение классов двух Thread-ов}
type
TMyThread1 = class(TThread)
private
{ Private declarations }
protected
procedure DoWork;
procedure Execute; override;
end;
TMyThread2 = class(TThread)
private
{ Private declarations }
protected
procedure DoWork;
procedure Execute; override;
end;
var Form1: TForm1;
T1 : TMyThread1;
T2 : TMyThread2;
implementation
procedure TMyThread1.Execute;
begin
{Пока процесс не прервали, выполняем DoWork}
while not Terminated do
Synchronize(DoWork);
end;
procedure TMyThread2.Execute;
begin
{Пока процесс не прервали, выполняем DoWork}
while not Terminated do
Synchronize(DoWork);
end;
procedure TMyThread1.DoWork;
begin
{Пытаемся победить второй процесс :-)}
Form1.CheckBox1.Checked := True;
end;
procedure TMyThread2.DoWork;
begin
{Пытаемся победить первый процесс :-)}
Form1.CheckBox1.Checked := False;
end;
procedure TForm1.Button1Click(Sender: TObject);
begin
{Если кнопка называется Stop...}
if Button1.Caption = 'Stop' then begin
{Прерываем оба процесса}
T1.Terminate;
T2.Terminate;
{Изменяем название кнопки}
Button1.Caption := 'Start';
{Выходим из процедуры}
Exit;
end;
{Создаем и сразу запускаем два процесса}
T1 := TMyThread1.Create(False);
T2 := TMyThread2.Create(False);
{Здесь можно поэкспериментировать с приоритетами:
T1.Priority := tpLowest;
T2.Priority := tpHighest;
}
{Переименовываем кнопку}
Button1.Caption := 'Stop';
end;
|
P.S. Отличный пример работы с TThread можно найти в подкаталоге
Demos\Threads каталога, куда Вы установили Borland Delphi.
В этой статье отображены основные стороны работы с процессами (потоками)
Thread в Borland Delphi. Если у Вас есть вопросы - скидывайте их мне на E-mail:
snick@mailru.com, а еще лучше - пишите
в конференции этого сайта (Delphi. Общие вопросы), чтобы и другие пользователи
смогли увидеть Ваш вопрос и попытаться на него ответить!
| |
Внимание! Запрещается перепечатка данной
статьи или ее части без согласования с автором. Если вы хотите разместить эту
статью на своем сайте или издать в печатном виде, свяжитесь с автором.
Автор статьи: Карих Николай
Статья написана для сайта: Дельфи.Вокруг да около.
| |
Статьи из раздела Delphi Исходный текст{ **** UBPFD *********** by delphibase.endimus.ru ****
Зависимости: Windows, Messages
Автор: savva, savva@nm.ru, ICQ:126578975, Орел
Copyright: Сапронов Алексей (Savva)
Дата: 27 июня 2002 г.
**************************************************** }
{типы описываем }
const
CNT_LAYOUT = 2; // количество известных раскладок
ENGLISH = $409;
RUSSIAN = $419;
TKbdValue : array [1. Пример 1procedure TWebModule1.WebModule1WebActionItem1Action(Sender: TObject;
Request: TWebRequest; Response: TWebResponse;
var Handled: Boolean);
begin
Response.Content := "<html><body>Hello ISAPI!</body></html>";
end;
9. Нажмите на меню File | Save All, выберите имена main.pas и helloisapi.dpr
для файлов проекта и сохраните их на диск.
10. Нажмите на меню Project | Build helloisapi. Будет скомпилирован файл
helloisapi.dll. Шаг первый - создание HTML страницы. Для начала мы создадим две простеньких HTML страницы. Для их создания вы
можете воспользоваться вашим любимым HTML редактором. Создайте одну страницу с
одним рисунком и ссылкой на другую страницу. Я назову свои
delphiandprogramming.html и page2.html. Когда вы добавите картинку в страницу,
то редактор напишет что-то вроде: <img . src="http://www. TCoolBarКомпонент TCoolBar, это новая разновидность TToolBar. TCoolBar это элемент
управления, который обычно содержит в себе два или более TCoolBand-ов, размеры и
местоположение которых можно изменять во время выполнения программы. CoolBand в
свою очередь является областью элемента управления, которая может содержать
другие оконные контролы, главным образом панели инструментов, окошки
редактирования, выпадающие списки и анимация. Создание ISAPI библиотекиСоздание ISAPI DLL похоже на разработку любой стандартной DLL. Для этого
необходимо загрузить Delphi, в меню File выбрать пункт New,
затем в диалоговом окне New Items выбрать пиктограмму Web Server Application
и нажать кнопку OK. Появится диалоговое окно New Web Server Application.
Пункт ISAPI/NSAPI Dynamic Link Library выбран по умолчанию, поэтому нажимаем
кнопку OK.
Вы попали в интерактивную среду разработки ISAPI расширения сервера.
|
|
|
|
|