Advertisement
Karasick

Untitled

Feb 12th, 2021
288
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Pascal 4.16 KB | None | 0 0
  1. Program NamesAddition;
  2. uses sysutils;
  3. const
  4.     BASE = 9; {система счислення}
  5.     N = 255;
  6.     ALLOW_LEADING_ZEROS = false; {чи дозволяються нулі на початку слова}
  7. var
  8.     a,b,c : string;
  9.     cnt_uniq : integer;
  10.     cnt_solutions : longint;
  11.     symbol_exist : array[0..N] of boolean;
  12.     val, pt : array[0..N] of integer;
  13.  
  14.  
  15. {Встановлення верхнього регістру для літер імені `s` та
  16.  відмітки про те, значення яких літер треба перебирати}
  17. function PrepareName(s : string) : string;
  18. var i : integer;
  19. begin
  20.     s := UpperCase(s);
  21.     for i := 1 to length(s) do
  22.         symbol_exist[ord(s[i])] := true;
  23.     exit(s);
  24. end;
  25.  
  26.  
  27. {Знаходження значення імені `s` з наявної комбінації літери-цифри}
  28. function GetVal(s : string) : longint;
  29. var i, res : longint;
  30. begin
  31.     res := 0;
  32.     for i := 1 to length(s) do
  33.         res := res * base + val[pt[ord(s[i])]];
  34.     GetVal := res;
  35. end;
  36.  
  37.  
  38. {Підстановка замість цифр у імені `s` значень замість літер}
  39. function GetStr(s : string) : string;
  40. var i,x : integer;
  41.     res : string;
  42. begin
  43.     res := '';
  44.     for i := 1 to length(s) do begin
  45.         x := val[pt[ord(s[i])]];
  46.         if x < 10 then
  47.             res := res + chr(x+48)
  48.         else
  49.             res := res + chr(x-10+97);
  50.        
  51.     end;
  52.     exit(res);
  53. end;
  54.  
  55.  
  56. {Виведення знайденої комбінація літер-цифер}
  57. procedure Print();
  58. var i : integer;
  59. begin
  60.     cnt_solutions := cnt_solutions + 1;
  61.    
  62.     WriteLn();
  63.     for i := 1 to N do if symbol_exist[i] then Write(chr(i)); WriteLn();
  64.     for i := 1 to N do if symbol_exist[i] then Write(val[pt[i]]); WriteLn();
  65.    
  66.     WriteLn(GetStr(a), ' + ', GetStr(b), ' = ', GetStr(c), ' [', base, '-base]');
  67.     if base <> 10 then
  68.         WriteLn(GetVal(a), ' + ', GetVal(b), ' = ', GetVal(c), ' [10-base]');
  69.    
  70. end;
  71.  
  72.  
  73. {Перевірка, що знайдена комбінація літери-цифри задовольняє умові}
  74. function Check() : boolean;
  75. begin
  76.     if not ALLOW_LEADING_ZEROS then
  77.     begin
  78.         if (length(a) > 1) and (val[pt[ord(a[1])]] = 0) then exit(false);
  79.         if (length(b) > 1) and (val[pt[ord(b[1])]] = 0) then exit(false);
  80.         if (length(c) > 1) and (val[pt[ord(c[1])]] = 0) then exit(false);
  81.     end;
  82.     exit(GetVal(a)+GetVal(b) = GetVal(c));
  83. end;
  84.  
  85.  
  86. {Рекурсивний перебір за O(BASE!) операцій}
  87. procedure RecUniq(pos : integer);
  88. var i,t : integer;
  89. begin
  90.     if pos = 0 then
  91.     begin
  92.         if Check() then
  93.             Print();
  94.         exit();
  95.     end;
  96.  
  97.     for i := 0 to pos do
  98.     begin
  99.         t := val[i]; val[i] := val[pos]; val[pos] := t;
  100.         RecUniq(pos-1);
  101.         t := val[i]; val[i] := val[pos]; val[pos] := t;
  102.     end;
  103. end;
  104.  
  105.  
  106. {Рекурсивний перебір за O(N^BASE) операцій, де N -- кількість різних букв у іменах}
  107. procedure RecNotUniq(pos : integer);
  108. var i : integer;
  109. begin
  110.     if pos = cnt_uniq then
  111.     begin
  112.         if Check() then
  113.             Print();
  114.         exit();
  115.     end;
  116.  
  117.     for i := 0 to base-1 do
  118.     begin
  119.         val[pos] := i;
  120.         RecNotUniq(pos+1);
  121.     end;
  122. end;
  123.  
  124.  
  125. procedure Bruteforce();
  126. var i : integer;
  127. begin
  128.    
  129.     for i := 0 to N do
  130.         if symbol_exist[i] then begin
  131.             pt[i] := cnt_uniq;
  132.             cnt_uniq := cnt_uniq + 1;
  133.         end;
  134.  
  135.     for i := 0 to base-1 do
  136.         val[i] := i;
  137.    
  138.    
  139.     {WriteLn('Unique numbers:');}
  140.     RecUniq(base-1);
  141.  
  142.     {WriteLn('Non-unique numbers:');
  143.     RecNotUniq(0);}
  144. end;
  145.  
  146.  
  147. begin
  148.     a := 'Anna'; b := 'Luisa'; c := 'Sussen';  
  149.     a := 'Karl'; b := 'Michel'; c := 'Kramek';
  150.  
  151.     a := PrepareName(a);
  152.     b := PrepareName(b);
  153.     c := PrepareName(c);
  154.    
  155.     writeln(a, ' + ', b, ' = ', c, ' [', base, '-base]');
  156.     writeln('Run bruteforce...');
  157.     cnt_solutions := 0;
  158.     Bruteforce();
  159.     WriteLn('Finished. Found ', cnt_solutions, ' solution(s)!');
  160. end.
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement