Advertisement
deced

Untitled

May 25th, 2021
131
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 15.11 KB | None | 0 0
  1. unit Unit2;
  2.  
  3. interface
  4.  
  5. uses
  6. Winapi.Windows, Winapi.Messages, System.SysUtils, System.Variants,
  7. System.Classes, Vcl.Graphics,
  8. Vcl.Controls, Vcl.Forms, Vcl.Dialogs, Vcl.StdCtrls, Vcl.Samples.Spin,
  9. Vcl.Menus, Graph, LinkList, MatrixInt, Node, Vcl.ExtCtrls, Vcl.Grids;
  10.  
  11. type
  12. // TIntMatrix = Array of Array of Integer;
  13. TIntMatrix = TMatrixInt;
  14. TIntArr = TArrInt;
  15. TLabelMatrix = Array of Array of TLabel;
  16.  
  17. TMainForm = class(TForm)
  18. Label1: TLabel;
  19. MainMenu1: TMainMenu;
  20. NInputClick: TMenuItem;
  21. SaveDialog1: TSaveDialog;
  22. OpenDialog1: TOpenDialog;
  23. SpinEditLine: TSpinEdit;
  24. SpinEditColumn: TSpinEdit;
  25. Label3: TLabel;
  26. Label4: TLabel;
  27. ButtonCreate: TButton;
  28. Label5: TLabel;
  29. ButtonResult: TButton;
  30. Label6: TLabel;
  31. Label7: TLabel;
  32. ButtonDelete: TButton;
  33. EditTest: TEdit;
  34. N1: TMenuItem;
  35. N2: TMenuItem;
  36. PopupMenu1: TPopupMenu;
  37. N3: TMenuItem;
  38. N4: TMenuItem;
  39. MatrixGrid: TStringGrid;
  40. procedure SpinEditLineKeyPress(Sender: TObject; var Key: Char);
  41. procedure ButtonCreateClick(Sender: TObject);
  42. procedure ButtonDeleteClick(Sender: TObject);
  43. procedure EditTestKeyPress(Sender: TObject; var Key: Char);
  44. procedure ButtonResultClick(Sender: TObject);
  45. procedure NInputClickClick(Sender: TObject);
  46. procedure N2Click(Sender: TObject);
  47. procedure FormCloseQuery(Sender: TObject; var CanClose: Boolean);
  48. procedure NOutputClickClick(Sender: TObject);
  49. procedure SpinEditLineKeyDown(Sender: TObject; var Key: Word;
  50. Shift: TShiftState);
  51. procedure EditTestKeyDown(Sender: TObject; var Key: Word;
  52. Shift: TShiftState);
  53. Function CheckFileExtension(Address: String): Boolean;
  54. Procedure OutputFile(Address: String);
  55. procedure N3Click(Sender: TObject);
  56. procedure N4Click(Sender: TObject);
  57. function CheckMatrix(): Boolean;
  58. procedure FormCreate(Sender: TObject);
  59. procedure MatrixGridClick(Sender: TObject);
  60. procedure ClearMatrix();
  61.  
  62. private
  63. { Private declarations }
  64. public
  65. { Public declarations }
  66. end;
  67.  
  68. const
  69. MAX_LINE_MATRIX = 7;
  70. MAX_COLUMN_MATRIX = 15;
  71. MIN_SIZE_MATRIX = 2;
  72.  
  73. var
  74. MainForm: TMainForm;
  75. MatrixInt: TIntMatrix;
  76. MatrixResult: TLabelMatrix;
  77. ListCycle: TLinkList<String>;
  78.  
  79. implementation
  80.  
  81. {$R *.dfm}
  82.  
  83. uses OutputGraph;
  84.  
  85. function TMainForm.CheckMatrix(): Boolean;
  86. var
  87. I, J: Integer;
  88. begin
  89. ButtonResult.Enabled := true;
  90. try
  91. for I := 1 to MatrixGrid.RowCount-1 do
  92. for J := 1 to MatrixGrid.ColCount-1 do
  93. if not ((StrToInt(MatrixGrid.Cells[J, I]) = 0) or
  94. (StrToInt(MatrixGrid.Cells[J, I]) = 1)) then
  95. ButtonResult.Enabled := false;
  96. except
  97. ButtonResult.Enabled := false;
  98. end;
  99. if not ButtonResult.Enabled then
  100. MessageDlg('Матрица задана некорректно', mtError, [mbOK], 0);
  101. CheckMatrix := ButtonResult.Enabled;
  102. end;
  103.  
  104. procedure TMainForm.EditTestKeyDown(Sender: TObject; var Key: Word;
  105. Shift: TShiftState);
  106. begin
  107. TEdit(Sender).ReadOnly := (Shift = [ssShift]) or (Shift = [ssCtrl]);
  108. end;
  109.  
  110. procedure TMainForm.EditTestKeyPress(Sender: TObject; var Key: Char);
  111. begin
  112. With (Sender as TEdit) do
  113. begin
  114. if not(Key in ['0' .. '1', #8]) then
  115. Key := #0;
  116. if (Length(Text) > 0) and not(Key = #8) then
  117. Key := #0;
  118. end;
  119. end;
  120.  
  121. procedure TMainForm.FormCloseQuery(Sender: TObject; var CanClose: Boolean);
  122. begin
  123. if MessageDlg('Вы действительно хотите выйти?', mtWarning, [mbYes, mbNo], 0)
  124. = mrNo then
  125. CanClose := false;
  126. end;
  127.  
  128. procedure TMainForm.FormCreate(Sender: TObject);
  129. begin
  130. MatrixGrid.Cells[0, 1] := '1';
  131. MatrixGrid.Cells[0, 2] := '2';
  132. MatrixGrid.Cells[1, 0] := 'A';
  133. MatrixGrid.Cells[2, 0] := 'B';
  134. end;
  135.  
  136. procedure TMainForm.MatrixGridClick(Sender: TObject);
  137. begin
  138. ButtonResult.Enabled := true;
  139. end;
  140.  
  141. Procedure CreateMatrix(Line, Column: Integer);
  142. begin
  143. MainForm.MatrixGrid.RowCount := Line+1;
  144. MainForm.MatrixGrid.ColCount := Column+1;
  145. MainForm.MatrixGrid.Height := MainForm.MatrixGrid.RowCount * 22;
  146. MainForm.MatrixGrid.Width := MainForm.MatrixGrid.ColCount * 22;
  147. end;
  148.  
  149. procedure TMainForm.ButtonCreateClick(Sender: TObject);
  150. var
  151. Line, Column, I, J: Integer;
  152. IsCorrect: Boolean;
  153. begin
  154.  
  155. IsCorrect := true;
  156. Line := SpinEditLine.Value;
  157. Column := SpinEditColumn.Value;
  158. for I := 1 to Line do
  159. MatrixGrid.Cells[0, I] := IntToStr(I);
  160. for I := 1 to Column do
  161. MatrixGrid.Cells[I, 0] := Chr(Ord('A') + I - 1);
  162. if ((Line > MAX_LINE_MATRIX) or (Column > MAX_COLUMN_MATRIX)) and IsCorrect
  163. then
  164. begin
  165. MessageDlg('Размеры матрицы не должны превышать 7', mtError, [mbOK], 0);
  166. IsCorrect := false;
  167. end;
  168. if IsCorrect then
  169. begin
  170. CreateMatrix(Line, Column);
  171. ButtonDelete.Enabled := true;
  172. ButtonCreate.Enabled := false;
  173. SpinEditLine.Enabled := false;
  174. SpinEditColumn.Enabled := false;
  175. NInputClick.Enabled := false;
  176. end;
  177. end;
  178.  
  179. procedure TMainForm.ClearMatrix();
  180. var
  181. I, J: Integer;
  182. begin
  183. for I := 1 to MatrixGrid.RowCount do
  184. for J := 1 to MatrixGrid.ColCount do
  185. MatrixGrid.Cells[J, I] := '';
  186. end;
  187.  
  188. procedure TMainForm.ButtonDeleteClick(Sender: TObject);
  189. var
  190. I, J, Num: Integer;
  191. begin
  192. ButtonDelete.Enabled := false;
  193. ButtonCreate.Enabled := true;
  194. SpinEditLine.Enabled := true;
  195. SpinEditColumn.Enabled := true;
  196. NInputClick.Enabled := true;
  197. ClearMatrix();
  198. end;
  199.  
  200. Procedure FillMatrix(Var MatrixInt: TIntMatrix);
  201. var
  202. I, J: Integer;
  203. begin
  204. SetLength(MatrixInt, MainForm.MatrixGrid.RowCount - 1,
  205. MainForm.MatrixGrid.ColCount - 1);
  206. for I := 0 to High(MatrixInt) do
  207. for J := 0 to High(MatrixInt[I]) do
  208. MatrixInt[I][J] :=
  209. StrToInt(MainForm.MatrixGrid.Cells[J + 1, I + 1]);
  210. end;
  211.  
  212. function IsGraphExist(Matrix: TIntMatrix): Boolean;
  213. var
  214. Temp, I, J: Integer;
  215. IsCorrect: Boolean;
  216. begin
  217. IsCorrect := true;
  218. for J := 0 to High(Matrix[0]) do
  219. begin
  220. Temp := 0;
  221. for I := 0 to High(Matrix) do
  222. if Matrix[I][J] = 1 then
  223. Inc(Temp);
  224. if (Temp <> 2) and (Temp <> 0) then
  225. begin
  226. MessageDlg('По данной матрице невозможно построить граф', mtError,
  227. [mbOK], 0);
  228. IsCorrect := false;
  229. end;
  230. end;
  231. IsGraphExist := IsCorrect;
  232. end;
  233.  
  234. function FillArrCycle(Line: String): TIntArr;
  235. var
  236. I, J: Integer;
  237. Arr: TIntArr;
  238. begin
  239. SetLength(Arr, (Length(Line) - 6) div 2);
  240. J := 0;
  241. I := 7;
  242. while (I < Length(Line)) do
  243. begin
  244. Arr[J] := StrToInt(Line[I]);
  245. Inc(J);
  246. I := I + 2;
  247. end;
  248. FillArrCycle := Arr;
  249. end;
  250.  
  251. procedure OutputGrpah(Graph: TGraph);
  252. var
  253. Arr: TIntArr;
  254. begin
  255. Arr := FillArrCycle(Graph.HamiltonianCycle.GetLinkByIndex(1).GetData);
  256. FormOutputGraph.FillLabelCyrcle(Graph.HamiltonianCycle);
  257. FormOutputGraph.PrintGraph(Graph.GetAdjMat, Arr);
  258. FormOutputGraph.ShowModal;
  259. end;
  260.  
  261. procedure CreateGraph(MatrixInt: TIntMatrix);
  262. var
  263. Graph: TGraph;
  264. begin
  265. Graph := TGraph.Create(Length(MatrixInt));
  266. Graph.FillAdjMat(MatrixInt);
  267. ListCycle := Graph.HamiltonianCycle;
  268. if ListCycle.GetSize = 0 then
  269. MessageDlg('В данном графе отсутсвуют гамильтоновы циклы', mtError,
  270. [mbOK], 0)
  271. else
  272. OutputGrpah(Graph);
  273. end;
  274.  
  275. procedure TMainForm.ButtonResultClick(Sender: TObject);
  276. var
  277. MatrixInt: TIntMatrix;
  278. Arr: TIntArr;
  279. begin
  280. if CheckMatrix then
  281. begin
  282. FillMatrix(MatrixInt);
  283. if IsGraphExist(MatrixInt) then
  284. CreateGraph(MatrixInt);
  285. end;
  286. end;
  287.  
  288. procedure TMainForm.SpinEditLineKeyDown(Sender: TObject; var Key: Word;
  289. Shift: TShiftState);
  290. begin
  291. TEdit(Sender).ReadOnly := (Shift = [ssShift]) or (Shift = [ssCtrl]);
  292. end;
  293.  
  294. procedure TMainForm.SpinEditLineKeyPress(Sender: TObject; var Key: Char);
  295. begin
  296. Key := #0;
  297. end;
  298.  
  299. Function CheckNumberOfLines(Address: String): Integer;
  300. Var
  301. Line, Num: Integer;
  302. InputFile: TextFile;
  303. Begin
  304. AssignFile(InputFile, Address);
  305. Reset(InputFile);
  306. Line := 0;
  307. While (Not SeekEof(InputFile)) Do
  308. Begin
  309. Read(InputFile, Num);
  310. If (SeekEoln(InputFile)) Then
  311. Inc(Line);
  312. End;
  313. Close(InputFile);
  314. CheckNumberOfLines := Line;
  315. End;
  316.  
  317. Function CheckNumberOfColumns(Address: String): Integer;
  318. Var
  319. Columns, Num: Integer;
  320. InputFile: TextFile;
  321. Begin
  322. AssignFile(InputFile, Address);
  323. Reset(InputFile);
  324. Columns := 0;
  325. While (Not SeekEoln(InputFile)) Do
  326. Begin
  327. Read(InputFile, Num);
  328. Inc(Columns);
  329. End;
  330. Close(InputFile);
  331. CheckNumberOfColumns := Columns;
  332. End;
  333.  
  334. Procedure ReadFile(Address: String);
  335. Var
  336. InputFile: TextFile;
  337. Lines, Columns, I, J, Temp: Integer;
  338. Begin
  339. Lines := CheckNumberOfLines(Address);
  340. Columns := CheckNumberOfColumns(Address);
  341. CreateMatrix(Lines, Columns);
  342. AssignFile(InputFile, Address);
  343. Reset(InputFile);
  344. Dec(Lines);
  345. Dec(Columns);
  346. For I := 0 To Lines Do
  347. For J := 0 To Columns Do
  348. begin
  349. Read(InputFile, Temp);
  350. MainForm.MatrixGrid.Cells[J + 1, I + 1] := IntToStr(Temp);
  351. end;
  352. Close(InputFile);
  353. End;
  354.  
  355. Function IsCorrectSizeFile(Address: String): Boolean;
  356. Var
  357. IsCorrect: Boolean;
  358. InputFile: TextFile;
  359. Begin
  360. AssignFile(InputFile, Address);
  361. Reset(InputFile);
  362. If (EoF(InputFile)) Then
  363. Begin
  364. MessageDlg('Файл пустой', mtError, [mbOK], 0);
  365. IsCorrect := false;
  366. End
  367. Else
  368. IsCorrect := true;
  369. Close(InputFile);
  370. IsCorrectSizeFile := IsCorrect;
  371. End;
  372.  
  373. Procedure PrintErrorFile(IsCorrect: Boolean);
  374. Begin
  375. If (Not IsCorrect) Then
  376. MessageDlg('Данные в указанном файле не соответствуют условию', mtError,
  377. [mbOK], 0);
  378. End;
  379.  
  380. Function TMainForm.CheckFileExtension(Address: String): Boolean;
  381. Var
  382. N: Integer;
  383. IsCorrect: Boolean;
  384. Begin
  385. N := Length(Address);
  386. IsCorrect := false;
  387. if (Address[N] = 't') and (Address[N - 1] = 'x') and (Address[N - 2] = 't')
  388. then
  389. IsCorrect := true
  390. else
  391. MessageDlg('Файл должен иметь расширение .txt', mtError, [mbOK], 0);
  392. CheckFileExtension := IsCorrect;
  393. End;
  394.  
  395. Function IsCorrectFile(Address: String): Boolean;
  396. Var
  397. IsCorrect: Boolean;
  398. InputFile: TextFile;
  399. Num: Integer;
  400. Begin
  401. AssignFile(InputFile, Address);
  402. Reset(InputFile);
  403. IsCorrect := true;
  404. While ((Not EoF(InputFile)) And IsCorrect) Do
  405. Begin
  406. Try
  407. Read(InputFile, Num);
  408. if (Num <> 0) and (Num <> 1) then
  409. IsCorrect := false;
  410. Except
  411. IsCorrect := false;
  412. End;
  413. End;
  414. Close(InputFile);
  415. if IsCorrect then
  416. begin
  417. if (CheckNumberOfLines(Address) < MIN_SIZE_MATRIX) or
  418. ((CheckNumberOfColumns(Address) < MIN_SIZE_MATRIX)) then
  419. IsCorrect := false;
  420. if (CheckNumberOfLines(Address) > MAX_LINE_MATRIX) or
  421. ((CheckNumberOfColumns(Address) > MAX_COLUMN_MATRIX)) then
  422. IsCorrect := false;
  423. end;
  424. PrintErrorFile(IsCorrect);
  425. IsCorrectFile := IsCorrect;
  426. End;
  427.  
  428. Function IsFileExist(Address: String): Boolean;
  429. Var
  430. IsCorrect: Boolean;
  431. Begin
  432. If FileExists(Address) Then
  433. IsCorrect := true
  434. Else
  435. Begin
  436. IsCorrect := false;
  437. MessageDlg('Указанного файла не существует', mtError, [mbOK], 0);
  438. End;
  439. IsFileExist := IsCorrect;
  440. End;
  441.  
  442. procedure TMainForm.N2Click(Sender: TObject);
  443. begin
  444. MainForm.Close;
  445. end;
  446.  
  447. procedure TMainForm.N3Click(Sender: TObject);
  448. begin
  449. MessageBox(Application.Handle,
  450. 'Выполнила студентка группы 051007, Герасимович Дарья',
  451. 'Об авторе', mb_ok);
  452. end;
  453.  
  454. procedure TMainForm.N4Click(Sender: TObject);
  455. begin
  456. MessageBox(Application.Handle,
  457. 'Граф задан матрицей инциденций. Разработать программу нахождения ' +
  458. #10#13 + 'всех гамильтоновых циклов в графе. Граф визуализировать. Найденный цикл выделить цветом.',
  459. 'О программе', mb_ok);
  460. end;
  461.  
  462. procedure TMainForm.NInputClickClick(Sender: TObject);
  463. var
  464. InputFile: TextFile;
  465. IsCorrect: Boolean;
  466. begin
  467. repeat
  468. IsCorrect := true;
  469. if OpenDialog1.Execute then
  470. begin
  471. IsCorrect := IsFileExist(OpenDialog1.FileName) and
  472. CheckFileExtension(OpenDialog1.FileName) and
  473. IsCorrectSizeFile(OpenDialog1.FileName) and
  474. IsCorrectFile(OpenDialog1.FileName);
  475. if IsCorrect then
  476. begin
  477. ReadFile(OpenDialog1.FileName);
  478. SpinEditLine.Value := CheckNumberOfLines(OpenDialog1.FileName);
  479. SpinEditColumn.Value :=
  480. CheckNumberOfColumns(OpenDialog1.FileName);
  481. ButtonDelete.Enabled := true;
  482. ButtonCreate.Enabled := false;
  483. SpinEditLine.Enabled := false;
  484. SpinEditColumn.Enabled := false;
  485. NInputClick.Enabled := false;
  486. end;
  487. end;
  488. until IsCorrect;
  489. end;
  490.  
  491. Procedure TMainForm.OutputFile(Address: String);
  492. Var
  493. OutputFile: TextFile;
  494. IsCorrect: Boolean;
  495. I, J: Integer;
  496. Begin
  497. AssignFile(OutputFile, Address);
  498. Rewrite(OutputFile);
  499. Writeln(OutputFile, 'Матрица: ');
  500. for I := 0 to MatrixGrid.RowCount - 1 do
  501. begin
  502. for J := 0 to MatrixGrid.ColCount - 1 do
  503. Write(OutputFile, MatrixGrid.Cells[J + 1, I + 1] + ' ');
  504. Writeln(OutputFile);
  505. end;
  506. Writeln(OutputFile, 'Гамильтоновы циклы: ');
  507. for I := 1 to ListCycle.GetSize do
  508. begin
  509. Writeln(OutputFile, IntToStr(I) + '-ый ' + ListCycle.GetLinkByIndex
  510. (I).GetData);
  511. end;
  512. CloseFile(OutputFile);
  513. End;
  514.  
  515. procedure TMainForm.NOutputClickClick(Sender: TObject);
  516. var
  517. IsCorrect: Boolean;
  518. begin
  519. repeat
  520. IsCorrect := true;
  521. if SaveDialog1.Execute then
  522. begin
  523. IsCorrect := CheckFileExtension(SaveDialog1.FileName);
  524. if IsCorrect then
  525. begin
  526. OutputFile(SaveDialog1.FileName);
  527. ShowMessage('Результат успешно сохранён');
  528. end;
  529. end;
  530. until IsCorrect;
  531. end;
  532.  
  533. end.
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement