Здравствуйте уважаемые эксперты! Есть следующее задание: написать программу, в которой два потока заполняют таблицу умножения. Первый поток заполняет все нечетные строки, второй – все четные. Использовать глобальную переменную для хранения текущего индекса в строке. Использовать семафоры. Вот получившийся код:
Код:
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls, ExtCtrls, TeEngine, Series, TeeProcs, Chart, Buttons;
type
TForm1 = class(TForm)
RadioGroup1: TRadioGroup;
RadioGroup2: TRadioGroup;
BitBtn1: TBitBtn;
BitBtn2: TBitBtn;
procedure BitBtn1Click(Sender: TObject);
procedure BitBtn2Click(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;
var
Form1 : TForm1;
Matrix : array [1..9, 1.. 9] of integer;
Handles : array [0..1] of THandle;
ThreadID1, ThreadID2 : Cardinal;
i : integer;
hSemaphore : THandle = 0;
implementation
{$R *.dfm}
procedure FirstHandle;
var j, k, Sum : integer;
WaitReturn : DWORD;
begin
for i := 1 to 9 do
begin
WaitReturn := WaitForSingleObject(hSemaphore, INFINITE);
if WaitReturn = WAIT_OBJECT_0 then
begin
if i mod 2 <> 0 then
for j := 1 to 9 do
begin
Sum := 0;
for k := 1 to j do
begin
Sum := Sum + i;
Sleep(1);
Matrix[i, j] := Sum;
end;
write(Matrix[i,j] : 3);
end;
writeln;
end;
ReleaseSemaphore(hSemaphore, 1, nil);
end;
end;
procedure SecondHandle;
var j, k, Sum : integer;
WaitReturn : DWORD;
begin
for i := 1 to 9 do
begin
WaitReturn := WaitForSingleObject(hSemaphore, INFINITE);
if WaitReturn = WAIT_OBJECT_0 then
begin
if i mod 2 = 0 then
for j := 1 to 9 do
begin
Sum := 0;
for k := 1 to j do
begin
Sum := Sum + i;
Sleep(1);
Matrix[i, j] := Sum;
end;
write(Matrix[i,j] : 3);
end;
writeln;
end;
ReleaseSemaphore(hSemaphore, 1, nil);
end;
end;
procedure TForm1.BitBtn1Click(Sender: TObject);
var i, j : integer;
Reason : DWORD;
begin
hSemaphore := CreateSemaphore(nil, 1, 1, nil);
Handles[0] := CreateThread(nil, 0, @FirstHandle, nil, CREATE_SUSPENDED, ThreadID1);
Handles[1] := CreateThread(nil, 0, @SecondHandle, nil, CREATE_SUSPENDED, ThreadID2);
case RadioGroup1.ItemIndex of
0 : SetThreadPriority(Handles[0], Thread_Priority_Time_Critical);
1 : SetThreadPriority(Handles[0], Thread_Priority_Highest);
2 : SetThreadPriority(Handles[0], Thread_Priority_Above_Normal);
3 : SetThreadPriority(Handles[0], Thread_Priority_Normal);
4 : SetThreadPriority(Handles[0], Thread_Priority_Below_Normal);
5 : SetThreadPriority(Handles[0], Thread_Priority_Idle);
end;
case RadioGroup2.ItemIndex of
0 : SetThreadPriority(Handles[1], Thread_Priority_Time_Critical);
1 : SetThreadPriority(Handles[1], Thread_Priority_Highest);
2 : SetThreadPriority(Handles[1], Thread_Priority_Above_Normal);
3 : SetThreadPriority(Handles[1], Thread_Priority_Normal);
4 : SetThreadPriority(Handles[1], Thread_Priority_Below_Normal);
5 : SetThreadPriority(Handles[1], Thread_Priority_Idle);
end;
ResumeThread(Handles[0]);
ResumeThread(Handles[1]);
end;
procedure TForm1.BitBtn2Click(Sender: TObject);
begin
Form1.Close;
end;
end.
Но программа после вывода таблицы умножения (не всегда корректного, может иногда пропускать некоторые строки) продолжает выводить какой-то мусор.. Подскажите в чем ошибка? Заранее огромное спасибо!