Фірма Computer Recognіtііon Systems (CRS) продає серію нейрокомп’ютерів WІZARD/CRS 1000, призначених для обробки відеозображень. Розмір вхідного зображення 512 x 512 пікселей. Модель CRS 1000 вже знайшла застосування в промислових системах автоматичного контролю.
Сьогодні на ринку представлено багато моделей нейрокомп’ютерів. Насправді їх, очевидно, набагато більше, але найбільш могутні і перспективні моделі як і раніше створюються за замовленнями військових. Нажаль, не маючи достатньої інформації про моделі спеціального призначення, важко скласти уявлення про істинні можливості сучасних комп'ютерів.
{Програмна реалізація нейронної мережі Хебба}
unit rou_main;
interface
uses
Windows, Messages, SysUtils, Variants, Classes,
Graphics, Controls, Forms,Dialogs, ExtCtrls,
StdCtrls, Grids, Buttons;
const
yes='y'; //Стан активності/не активності
no='n'; //комірки елемента TStringGrid
str=10; //Розміри нейрону
stol=10;
type
{Користувацькі типи даних}
one_element= array [0..str*stol+4] of integer; //Опис нейрона
W_type= array [0..3,0..str*stol] of integer; //Опис нейронної мережі
S_type=array [0..3] of integer; //Масив сумарних
//вихідних результатів
TForm1 = class(TForm)
{Опис елементів форми}
Panel1: TPanel;
s1: TStringGrid; //Поле першого нейрону
l1: TLabel;
Bevel1: TBevel;
Memo1: TMemo; //Інформаційне поле
Label2: TLabel;
s2: TStringGrid; //Поле другого нейрону
l2: TLabel;
s3: TStringGrid; //Поле третього нейрону
l3: TLabel;
s4: TStringGrid; //Поле четвертого нейрону
l4: TLabel;
s5: TStringGrid; //Поле для символів, що розпізнаються
Label6: TLabel;
BitBtn1: TBitBtn; //Кнопка "Teaching"
BitBtn2: TBitBtn; //Кнопка "Find"
BitBtn3: TBitBtn; //Кнопка "Exit"
BitBtn14: TBitBtn; //Кнопка "Clean"
BitBtn8: TBitBtn; //Кнопка "Clean"
BitBtn11: TBitBtn; //Кнопка "Clean"
BitBtn15: TBitBtn; //Кнопка "Clean"
BitBtn18: TBitBtn; //Кнопка "Clean"
BitBtn4: TBitBtn; //Кнопка "Load"
BitBtn5: TBitBtn; //Кнопка "Save"
{Процедури і функції основної форми}
procedure s1DrawCell(Sender: TObject; ACol, ARow: Integer;
Rect: TRect; State: TGridDrawState);
procedure FormCreate(Sender: TObject);
procedure s1MouseDown(Sender: TObject; Button: TMouseButton;
Shift: TShiftState; X, Y: Integer);
procedure BitBtn1Click(Sender: TObject);
procedure Initialization_M;
procedure Vivod_W (W:W_type);
procedure BitBtn2Click(Sender: TObject);
procedure BitBtn4Click(Sender: TObject);
procedure BitBtn5Click(Sender: TObject);
procedure BitBtn14Click(Sender: TObject);
procedure BitBtn8Click(Sender: TObject);
procedure BitBtn11Click(Sender: TObject);
procedure BitBtn15Click(Sender: TObject);
procedure BitBtn18Click(Sender: TObject);
end;
{Допоміжні процедури і функції}
procedure Raschet_b1;
function convert (s: string): integer;
procedure Read_str_grd (str_grd:TStringGrid;var M:one_element);
function Check_result (num_letter,num_nero:integer):boolean;
procedure Obuchenie(num_letter,num_nero:byte);
function Check_Learning :boolean;
procedure checkFillM5(Y:integer);
procedure clear_stringgrid (Sender:Tobject);
function mask_el: W_type;
procedure re_mask_el(mask_elem: W_type);
{Основні змінні}
var
Form1 :TForm1; //Змінна форми
M :array [0..4] of one_element; //Масив, що описує нейрони мережі
W :W_type; //Опис нейронної мережі
prizn :boolean;
S :S_type;
i :integer;
f :file of W_type; //Змінна файлу для збереження
//стану нейронної мережі
implementation
{$R *.dfm}
{Процедура малювання форми}
procedure TForm1.s1DrawCell(Sender: TObject; ACol, ARow: Integer;
Rect: TRect; State: TGridDrawState);
begin
(sender as tstringgrid).canvas.Brush.Color:=$a08000;
if (sender as tstringgrid).Cells[Acol,Arow]=yes then
(sender as tstringgrid).canvas.FillRect(Rect)
else begin
(sender as tstringgrid).canvas.Brush.Color:=clCream;
(sender as tstringgrid).canvas.FillRect(Rect)
end;
end;
{Процедура створення форми}
procedure TForm1.FormCreate(Sender: TObject);
begin
prizn:=false;
clear_stringgrid (s1); //Очищення поля нейрону 1
clear_stringgrid (s2); //Очищення поля нейрону 2
clear_stringgrid (s3); //Очищення поля нейрону 3
clear_stringgrid (s4); //Очищення поля нейрону 4
clear_stringgrid (s5); //Очищення поля нейрону 5
end;
{Процедура активації комірки нейрону}
procedure TForm1.s1MouseDown(Sender: TObject; Button: TMouseButton;
Shift: TShiftState; X, Y: Integer);
begin
if (sender as tstringgrid).Cells[(sender as tstringgrid).Col,(sender as tstringgrid).Row]=yes then
(sender as tstringgrid).Cells[(sender as tstringgrid).Col,(sender as tstringgrid).Row]:=no
else (sender as tstringgrid).Cells[(sender as tstringgrid).Col,(sender as tstringgrid).Row]:=yes;
end;
{Процедура навчання нейронної мережі}
procedure TForm1.BitBtn1Click(Sender: TObject);
var i,j:integer;
begin
Memo1.Clear; //Очищення інформаційного поля
Initialization_M; //Ініціалізація масиву W для навчання
Memo1.Lines.Add('Initialization of the weight ratio of neuron connections');
Vivod_W (W); //Вивід масиву W
Raschet_b1; //Розрахунок важелів зв’язків нейронів
//для першого нейрону
Memo1.Lines.Add('Calculation the firs simbol:');
Vivod_W (W); //Вивід масиву W
{Навчання першого нейрону}
Check_result (0,0);
Check_result (0,1);
Check_result (0,2);
Check_result (0,3);
{Навчання інших нейронів}
for i:=1 to 3 do
for j:= 0 to 3 do
begin
while not Check_result (i,j) do
Obuchenie (i,j); //Навчання нейрону доки не отримано
//жаданий результат
end;
Memo1.Lines.Add('Result weight ratio ');
Vivod_W (W); //Вивід масиву W
if Check_Learning then Memo1.Lines.Add('Teaching is successful.')
else Memo1.Lines.Add('Teaching is impossible.');
BitBtn1.Enabled:=false; //Кнопка "Teaching" неактивна
BitBtn2.enabled:=true; //Кнопка "Find" активна
BitBtn5.enabled:=true; //Кнопка "Save" активна
end;
{Функція інтерпретації активності комірки нейрона}
function convert (s: string): integer;
begin
if s=yes then Result:=1
else Result:=-1;
end;
{Функція початкової ініціалізації масиву W}
procedure TForm1.Initialization_M;
var
str1 :string;
j,i :byte;
begin
{Зчитуємо зображення навчальних символів}
Read_str_grd (s1,M[0]);
Read_str_grd (s2,M[1]);
Read_str_grd (s3,M[2]);
Read_str_grd (s4,M[3]);
M[0,str*stol+1]:=1;
M[1,str*stol+2]:=1;
M[2,str*stol+3]:=1;
M[3,str*stol+4]:=1;
Memo1.Lines.Add('Giving of the set M:');
{Вивід на екран зчитаних даних}
for j:= 0 to length (M)-2 do
begin
for i:= 0 to length(M[j])-1 do str1:=str1+' '+inttostr(m[j,i]);
Memo1.Lines.Add(str1);
str1:='';
end;
end;
{Конвертація зображення на нейроні в числові дані}
procedure Read_str_grd (str_grd:TStringGrid;var M:one_element);
var i,j:integer;
begin
for i:=0 to str-1 do
for j:=0 to stol-1 do
M[i*stol+j+1]:=convert(str_grd.Cells[j,i]); //Інтерпретація значення
//комірок нейрона
M[0]:=1;
for i:= str*stol+1 to str*stol+4 do
M[i]:=-1;
end;
{Процедура виводу на екран вмісту масиву W}
procedure TForm1.Vivod_W (W:W_type);
var
i,j :byte;
str :string;
begin
for j:=0 to length (W)-1 do
begin
Form1.Memo1.Lines.Add('W'+inttostr(j+1)+':');
for i:=0 to length (W[j])-1 do str:=str+ ' '+inttostr (W[j,i]);
Form1.Memo1.Lines.Add(str);
str:='';
end;
end;
{Процедура розрахунку важелів зв’язків нейронів для першого нейрону}
procedure Raschet_b1;
var
i,j:byte;
begin
for j:=0 to length(W)-1 do
begin
for i:=0 to str*stol do
W[j,i]:=W[j,i]+M[0,i]*M[0,str*stol+J+1];
end;
end;
{Функція визначення правильності навчання}
function Check_result (num_letter,num_nero:integer):boolean;
var
i :integer;
stroke :string;
begin
s[num_nero]:=0;
for i:=0 to str*stol do
begin
s[num_nero]:=s[num_nero]+W[num_nero,i]*M[num_letter,i];
end;
stroka:='Sending the char '+inttostr(num_letter+1)+' to the
'+inttostr(num_nero+1)+' neuron';
Form1.Memo1.Lines.Add(stroka);
Form1.Memo1.Lines.Add('S'+inttostr(num_nero+1)+'='+inttostr(s[num_nero]));
if s[num_nero]<=0 then s[num_nero]:=-1
else s[num_nero]:=1;
if s[num_nero]= M[num_letter,str*stol+num_nero+1] then Result:=true
else begin
Result:=false;
Form1.Memo1.Lines.Add ('Incorrect result. Reteaching.');
end;
end;
{Процедура навчання нейрона}
procedure Obuchenie(num_letter,num_nero:byte);
var
p: integer;
begin
for p:=0 to str*stol do
W[num_nero,p]:=W[num_nero,p]+
M[num_letter,p]*M[num_letter,str*stol+num_nero+1];
end;
{Функція визначення правильності навчання нейронної мережі}
function Check_Learning :boolean;
var
res :array[0..3] of boolean;
s :array[0..3] of integer;
i,j,max,Y :integer;
s1 :string;
begin
{Подання на вхід мережі навчальних символів
і перевірка вірності реакції мережі на них}
for y:=0 to 3 do
begin
res[Y]:=false;
checkFillM5(Y);
for j:=0 to 3 do
begin
s[j]:=0;
for i:=0 to str*stol do
begin
s[j]:=s[j]+W[j,i]*M[4,i];
end;
end;
s1:='Identification of the Char ';
max:=s[0];
for i:=1 to 3 do
begin
s1:='S= '+inttostr(s[i]);
if s[i]>max then
begin
max:=s[i];
end;
end;
if max>0 then res[Y]:=true;
end;
result:=true;
{Перевірка чи на всі навчальні зображення мережа реагує вірно}
for i:=0 to 3 do
if not res[i] then
begin
result:=false;
break;
end;
end;
{Процедура вибору символа}
procedure checkFillM5(Y:integer);
var
i: integer;
begin
for i:=1 to str*stol do M[4,i]:=M[y,i]
end;
{Процедура визначення символу відповідно до навчальних зображень}
procedure TForm1.BitBtn2Click(Sender: TObject);
var
s: array [0..3] of integer;
i,j,k: byte;
max: integer;
strng: string;
begin
Memo1.Lines.Add('Identification of the Char ');
l1.Color:=clSilver;
l2.Color:=clSilver;
l3.Color:=clSilver;
l4.Color:=clSilver;
Read_str_grd (s5,M[4]); //Зчитуємо зображення символу
for j:=0 to 3 do
begin
s[j]:=0;
for i:=0 to str*stol do
begin
s[j]:=s[j]+W[j,i]*M[4,i]; //Подання символу на нейрони і
//визначення результуючих сум
end;
end;
max:=s[0];
k:=0;
for i:=0 to 3 do
begin
strng:=strng+'S'+inttostr(i+1)+'='+inttostr(s[i])+' ';
if s[i]>max then
begin
max:=s[i]; //Визначення максимальної суми
k:=i; //Визначення індексу вірного зображення
end;
end;
Memo1.Lines.Add(strng);
Memo1.Lines.Add('The char '+inttostr (K+1)+' has been identified.');
case (k+1) of //Позначення червоним кольором
//символу, що визначений як вірний
1:l1.Color:=clRed;
2:l2.Color:=clRed;
3:l3.Color:=clRed;
4:l4.Color:=clRed;
end;
BitBtn1.Enabled:=true; //Кнопка "Teaching" активна
end;
{Функція отримання маски навчальних символів}
function mask_el: W_type;
var
i,j :integer;
mask_elem :W_type;
begin
for i:=0 to str-1 do
for j:=0 to stol-1 do
begin
{Конвертація зображень навчальних символів у числові значення}
mask_elem[0,i*stol+j]:=convert(Form1.s1.Cells[j,i]);
mask_elem[1,i*stol+j]:=convert(Form1.s2.Cells[j,i]);
mask_elem[2,i*stol+j]:=convert(Form1.s3.Cells[j,i]);
mask_elem[3,i*stol+j]:=convert(Form1.s4.Cells[j,i]);
end;
Result:=mask_elem;
end;
{Процедура збереження в файлі "symbol.rou" стану нейронної мережі}
procedure TForm1.BitBtn5Click(Sender: TObject);
var
W1 :W_type;
begin
w1:=mask_el;
AssignFile(f, 'symbol.rou');
Rewrite(f); //Відкриття файлу для запису даних
write(f,W); //Запис стану нейронної мережі
write(f,W1); //Запис зображення навчальних символів
CloseFile(f);
Form1.Memo1.Lines.Add('Teaching Configuration data has been saved'+
' in data file symbol.rou');
MessageDlg('Teaching Configuration data has been saved'+
' in data file symbol.rou', mtInformation, [mbOk], 0);
BitBtn4.enabled:=true; //Кнопка "Load" активна
end;
{Процедура активації нейронів мережі згідно із зображенням}
procedure re_mask_el(mask_elem: W_type);
var
i,j :integer;
begin
{Очищення нейронів}
clear_stringgrid(Form1.s1);