Top.Mail.Ru
Мастера DELPHI, Delphi programming community Титульная страница Поиск, карта сайта Написать письмо 
| Новости | Поиск | FAQ | Статьи | Книги | Новости VCL |
| Форумы ЧАТ | Орешник | KOL и MCK |
Форумы -» Основная («Начинающим»)/ Базы / WinAPI / Компоненты / Сети / Media / Игры / Corba и COM / KOL / FreePascal / .Net / Прочее / RSDN.ORG

« предыдущая ветвь | форум | следующая ветвь »

Как оптимизировать скорость работы кода [D7, XP]


Страницы:   1 2

Kaer ©   (2008-06-10 13:08:00) 

При расчете если поставить 5000 очень долго(гдето больше 25 часов) идет проверка одинаковых значеный(выделено жирным), мож как нитьбудь это оптимизировать чтобы побыстрей проверялось?
unit Unit1;

interface

uses
 Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
 Dialogs, StdCtrls, shellapi, ComCtrls;

type
 TForm1 = class(TForm)
   Edit1: TEdit;
   Button1: TButton;
   Memo1: TMemo;
   Edit2: TEdit;
   CheckBox1: TCheckBox;
   procedure Button1Click(Sender: TObject);
 private
   { Private declarations }
 public
   { Public declarations }
 end;

var
 Form1: TForm1;
 x, y, a, b, i: integer;
 a_2, b_2: int64;
 ar: array of array of array of int64;
 f,d,l: TextFile;

implementation

{$R *.dfm}

procedure TForm1.Button1Click(Sender: TObject);
begin
 Memo1.Lines.Clear;
 AssignFile(d,'Пов_числа.txt');
 ReWrite(d);
 AssignFile(l,'Лог.txt');
 ReWrite(l);
 i:= StrToInt64(Edit1.Text);
 SetLength(ar,i+1,i+1,3);
 Writeln(l,TimeToStr(Time)+' - Запуск');
 Memo1.Lines.Add(TimeToStr(Time)+' - Запуск');

 //заполняю массив
 for a := 1 to i do
   for b := 1 to a do
   begin
     a_2:=a*a;
     b_2:=b*b;
     ar[b,a,0] := 2*a*b;
     ar[b,a,1] := a_2*a_2-b_2*b_2;
     ar[b,a,2] := a_2*a_2+b_2*b_2;
   end;
 Writeln(l,TimeToStr(Time)+' - Массив заполнен');
 Memo1.Lines.Add(TimeToStr(Time)+' - Массив заполнен');

 //Вывод таблицы
 If CheckBox1.Checked then
 begin
   AssignFile(f,'Таблица.txt');
   ReWrite(f);
   for a:= 1 to i do
   begin
     for b:=1 to a do if b=a then Writeln(f, IntToStr(ar[b,a,0])) else Write(f, IntToStr(ar[b,a,0])+' ');
     for b:=1 to a do if b=a then Writeln(f, IntToStr(ar[b,a,1])) else Write(f, IntToStr(ar[b,a,1])+' ');
     for b:=1 to a do if b=a then Writeln(f, IntToStr(ar[b,a,2])) else Write(f, IntToStr(ar[b,a,2])+' ');
     Writeln(f,' ');
   end;
   CloseFile(f);
   Writeln(l,TimeToStr(Time)+' - Таблица сгененирована');
   Memo1.Lines.Add(TimeToStr(Time)+' - Таблица сгененирована');
 end;

 //произвожу сравнение
 Memo1.Lines.Add(TimeToStr(Time)+' - Начало сравнения значений');
 for y := StrToInt(Edit2.Text) to i do
 begin
   for x := 1 to y do
   begin
     Memo1.Lines.Add(TimeToStr(Time)+' - Проверяется '+IntToStr(y)+' строка, '+IntToStr(x)+' столбец');
     for a:= 1 to i do
       for b:= 1 to a do
         if (ar[x,y,1]=ar[b,a,2]) then
         begin
           Writeln(d, IntToStr(ar[x,y,1]));
           Writeln(d,'Строка '+IntToStr(a)+' столбец '+IntToStr(b)+' - 3');
           Writeln(d,'Строка '+IntToStr(y)+' столбец '+IntToStr(x)+' - 2');
           Writeln(d,' ');
         end;
   end;
 Memo1.Lines.Add(TimeToStr(Time)+' - '+FloatToStr(100/i*y)+'%');
 end;


 Memo1.Lines.Add(TimeToStr(Time)+' - Раcчет закончен');
 CloseFile(d);
 CloseFile(l);
end;
end.


Kaer   (2008-06-10 18:12:00) [21]

ниче я просить не буду, но если честно плохо понял MBo, я не матиматик, я даже не программист :-)


Ega23   (2008-06-10 18:09:00) [22]


> MBo ©   (10.06.08 18:07) [11]


Щас у тебя код попросят.


MBo   (2008-06-10 18:07:00) [23]

>Прогрмма для одного кандидата(математика)
мда.... Опять  дедушку Эйлера опровергает, наверно.

Ну ладно, раз хочется попиндюриться, вот алгоритм со сложностью O(N^2*LogN)
Заводятся 2 массива структур Summ и Diff
record
 Res: Int64;
 A, B: Integer;
end
Res - сумма или разность A и B в степенях
Далее сортировка массивов  по полю Res
Затем делается один проход по обоим массивам одновременно. Индексы ставятся в начало.
Если Res больше у очередного элемента первого массива, увеличивается индекс для второго  массива и наборот.


Ega23   (2008-06-10 18:01:00) [24]


> Фух, надеюсь я понятно объеснил


Зря надеешься.


Kaer   (2008-06-10 17:54:00) [25]


> вставь в цикл Application.ProcessMessages через 100 итераций

пасибо, так намного лучше))


Правильный_Вася   (2008-06-10 17:50:00) [26]


> Мемо я использовал чтобы было видно програ работает или
> нет :-) а то ана подвисает.

вставь в цикл Application.ProcessMessages через 100 итераций


Kaer   (2008-06-10 17:45:00) [27]

Прогрмма для одного кандидата(математика) от там весь в науки и ему нужно знать на практике манипуляции данно программы. Смысл программы такой: Строиться таблица примерно такого вида

2
0
2

4 8
15 0
17 32

6 12 18
80 65 0
82 97 162

8 16 24 32
255 240 175 0
257 272 337 512

10 20 30 40 50
624 609 544 369 0
626 641 706 881 1250

Сдесть представлена таблица состоящая из 5 строк (3 подстроки не в счет:-)) и 5 столбцов (введено в Edit1 = 5)

i:= StrToInt64(Edit1.Text);
...
for a := 1 to i do
  for b := 1 to a do
  begin
    a_2:=a*a;
    b_2:=b*b;
    ar[b,a,0] := 2*a*b;
    ar[b,a,1] := a_2*a_2-b_2*b_2;
    ar[b,a,2] := a_2*a_2+b_2*b_2;
  end;

Формулы заполнения
1) с = 2*a*b
2) c = b^4-a^4
3) c = b^4+a^4
Затем нужно найти одинаковые значения во второй и третьих подстроках(!!! - это очень важно, не во второй второй, не в третей третей, а именно чтобы одно итоже значение было во второй подстроке и третей, пофигу каких строк и столбцов) что я и делаю методом перебора

Memo1.Lines.Add(TimeToStr(Time)+' - Начало сравнения значений');
for y := StrToInt(Edit2.Text) to i do
begin
  for x := 1 to y do
  begin
    Memo1.Lines.Add(TimeToStr(Time)+' - Проверяется '+IntToStr(y)+' строка, '+IntToStr(x)+' столбец');
    for a:= 1 to i do
      for b:= 1 to a do
        if (ar[x,y,1]=ar[b,a,2]) then
        begin
          Writeln(d, IntToStr(ar[x,y,1]));
          Writeln(d,'Строка '+IntToStr(a)+' столбец '+IntToStr(b)+' - 3');
          Writeln(d,'Строка '+IntToStr(y)+' столбец '+IntToStr(x)+' - 2');
          Writeln(d,' ');
        end;
  end;
Memo1.Lines.Add(TimeToStr(Time)+' - '+FloatToStr(100/i*y)+'%');
end;

Получается что если ввести в Edit1, 5000 (это он тока пока так требоет потом может больше захочет, 10000? 20000? может даже 30000 :-)) то программа будет сжирать гдето 1 gb, и очень долго перебирать знаения.

Мемо я использовал чтобы было видно програ работает или нет :-) а то ана подвисает. Подскажите другой способ какнибудь где она считает, я с удовольсвием его применю:-)

вот пример работы программы с числом 10 тока формула немного другая с 3 степенью а так все тоже самое
1) с = 2*a*b
2) c = b^3-a^3
3) c = b^3+a^3

2
0
2
4  8
7  0
9  16
6  12  18
26  19  0
28  35  54
8  16  24  32
63  56  37  0
65  72  91  128
10  20  30  40  50
124  117  98  61  0
126  133  152  189  250
12  24  36  48  60  72
215  208  189  152  91  0
217  224  243  280  341  432
14  28  42  56  70  84  98
342  335  316  279  218  127  0
344  351  370  407  468  559  686
16  32  48  64  80  96  112  128
511  504  485  448  387  296  169  0
513  520  539  576  637  728  855  1024
18  36  54  72  90  108  126  144  162
728  721  702  665  604  513  386  217  0
730  737  756  793  854  945  1072  1241  1458
20  40  60  80  100  120  140  160  180  200
999  992  973  936  875  784  657  488  271  0
1001  1008  1027  1064  1125  1216  1343  1512  1729  2000

Повторяющиеся числа:

728
Строка 8 столбец 6 - 3
Строка 9 столбец 1 - 2

189
Строка 5 столбец 4 - 3
Строка 6 столбец 3 - 2

152
Строка 5 столбец 3 - 3
Строка 6 столбец 4 - 2

91
Строка 4 столбец 3 - 3
Строка 6 столбец 5 - 2

513
Строка 8 столбец 1 - 3
Строка 9 столбец 6 - 2

217
Строка 6 столбец 1 - 3
Строка 9 столбец 8 - 2

Фух, надеюсь я понятно объеснил


MBo   (2008-06-10 14:42:00) [28]

Кстати, минимальное решение 422481^4 -  95800^4 =  217519^4 +  414560^4
так что пять тыщ - маловато будет ;))


MBo   (2008-06-10 14:12:00) [29]

Про неправильное использование визуального компонента внутри циклов уже сказали (можно использовать TStringList, либо BeginUpdate), а что вообще делает алгоритм? Какое-то странное сравнение непонятно чего непонятно с чем с алгоритмической  сложностью O(N^4), что для N=5000 дает порядка квадриллиона операций!


Правильный_Вася   (2008-06-10 13:58:00) [30]


> i: integer;
...
>  i:= StrToInt64(Edit1.Text);

А смысл?

> При расчете если поставить 5000

чего 5000?


Германн   (2008-06-10 13:55:00) [31]


> Kaer ©   (10.06.08 13:39) [2]

Запись в Мемо в каждой итерации цикла сжирает кучу времени.


Kaer   (2008-06-10 13:39:00) [32]

ну дык они же вроде срабатывают тока когда есть совпадения, а их по идеи и не должно быть (это какраз и надо проверить на практике), тем более если не будет записи то как еще можно узнать где совпадения?


Поросенок Винни-Пух   (2008-06-10 13:10:00) [33]

убрать мемо и преобразования


Страницы:   1 2

Наверх

Титульная страница Поиск, карта сайта Написать письмо