Vladislav_Bezruk

Untitled

Oct 8th, 2021 (edited)
178
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 7.98 KB | None | 0 0
  1. #include <iostream>
  2. #include <cassert>
  3. #include <cmath>
  4.  
  5. #define RUN_TEST 0 //1 - test on, 0 - test off
  6.  
  7. #define N 15 //len of number
  8.  
  9. #define FL_P 5 //len of float part
  10.  
  11. #define BASE 10 //base system
  12.  
  13. using namespace std;
  14.  
  15. class InfNum {
  16.     int sign = 1;
  17.     int data[N] = { 0 };
  18.     int size = 0;
  19.    
  20.     bool isZero() {
  21.         for (int i = N - 1; i >= size; i--) {
  22.             if (data[i] != 0) {
  23.                 return false;
  24.             }
  25.         }
  26.         return true;
  27.     }
  28.  
  29.     bool isOne() {
  30.         for (int i = N - 2; i >= size; i--) {
  31.             if (data[i] != 0 && i != N - 1 - FL_P) {
  32.                 return false;
  33.             }
  34.         }
  35.         return data[N - 1 - FL_P] == 1;
  36.     }
  37.  
  38.     void divByInt(InfNum &num, int intNum) {
  39.         for (int i = 0; i < N -1 ; i++) {
  40.             num.data[i + 1] += (num.data[i] % intNum) * BASE;
  41.             num.data[i] /= intNum;
  42.         }
  43.         num.data[N - 1] /= intNum;
  44.         num.updateSize();
  45.     }
  46.    
  47.     void swap(InfNum &a, InfNum &b) {
  48.         InfNum c = a;
  49.         a = b; b = c;
  50.     }
  51.  
  52.     int compare(InfNum &a, InfNum &b) {
  53.         for (int i = min(a.size, b.size); i < N; i++) {
  54.             if (a.data[i] > b.data[i]) {
  55.                 return 1;
  56.             }
  57.             if (a.data[i] < b.data[i]) {
  58.                 return -1;
  59.             }
  60.         }
  61.         return 0;
  62.     }
  63.  
  64.     static InfNum mult(InfNum &a, InfNum &b) {
  65.         InfNum c;
  66.         int iS, jS;
  67.  
  68.         for (int i = N - 1; i >= a.size; i--) {
  69.             iS = N - 1 - i - FL_P; 
  70.        
  71.             for (int j = N - 1; j >= b.size; j--) {
  72.                 jS = N - 1 - j - FL_P;
  73.                 int index = N - 1 - (iS + jS + FL_P);
  74.                 if (index >= 0) {
  75.                     c.data[index] += a.data[i] * b.data[j];
  76.                 }
  77.             }
  78.            
  79.         }
  80.         c.fixSystem();
  81.         c.sign = a.sign * b.sign;
  82.         c.updateSize();
  83.         return c;
  84.     }
  85.  
  86.     void binarySearch(InfNum l, InfNum r, InfNum &x, InfNum &a, InfNum &b, InfNum f(InfNum &x, InfNum &y)) { //search x in [l; r]
  87.         InfNum preX, res;
  88.         int fR;
  89.        
  90.         do {
  91.             preX = x;
  92.             x = l + r; divByInt(x, 2);
  93.             res = f(x, b);
  94.             fR = compare(a, res);
  95.            
  96.             if (fR == 1) {
  97.                 l = x;
  98.             } else {
  99.                 r = x;
  100.             }
  101.         } while (fR && compare(x, preX));
  102.         return;
  103.     }
  104.    
  105.     InfNum sum(InfNum &a, InfNum &b) {
  106.         InfNum c;
  107.  
  108.         for (int i = N - 1; i >= min(a.size, b.size); i--) {
  109.             c.data[i] = a.sign * a.data[i] + b.sign * b.data[i];
  110.         }
  111.         c.fixSystem();
  112.         return c;
  113.     }
  114.  
  115.     InfNum diff(InfNum &a, InfNum &b) {
  116.         InfNum c;
  117.  
  118.         for (int i = N - 1; i >= min(a.size, b.size); i--) {
  119.             c.data[i] = a.sign * a.data[i] - b.sign * b.data[i];
  120.         }
  121.         c.fixSystem();
  122.         return c;
  123.     }
  124.  
  125.     void fixSystem() {
  126.         updateSize();
  127.        
  128.         for (int i = N - 1; i > size - 1; i--) {
  129.             if (data[i] > BASE - 1) {
  130.                 data[i - 1] += data[i] / BASE;
  131.                 data[i] %= BASE;
  132.                
  133.             } else if (data[i] < 0) {
  134.                 int ost = ceil((-1 * float(data[i])) / BASE);
  135.                 data[i] += BASE * ost;
  136.                 data[i - 1] -= ost;    
  137.             }
  138.         }
  139.         if (data[size - 1] < 0) {
  140.                 sign *= -1;
  141.             for (int i = size - 1; i < N; i++) {
  142.                 data[i] *= -1;
  143.             }
  144.             fixSystem();
  145.         }
  146.     }
  147.  
  148.     InfNum div(InfNum &a, InfNum &b) {
  149.         int cmp = compare(a, b);
  150.         InfNum x;
  151.  
  152.         if (a.isZero() || b.isZero()) {
  153.             return zero();
  154.         }
  155.         if (cmp == 0) {
  156.             return one();
  157.         }
  158.         if (b.isOne()) {
  159.             return a;
  160.         }
  161.         binarySearch(zero(), a, x, a, b, mult);
  162.         return x;
  163.     }
  164.  
  165.     void updateSize() {
  166.         size = 0;
  167.         while (data[size] == 0) {
  168.             size++;
  169.         }
  170.     }
  171.    
  172.     InfNum zero() {
  173.         InfNum a;
  174.         return a;
  175.     }
  176.        
  177.     InfNum one() {
  178.         InfNum a;
  179.         a.set("1");
  180.         return a;
  181.     }
  182.    
  183.     public:
  184.         int toInt() {
  185.             int res = 0;
  186.  
  187.             for (int i = N - 1 - FL_P; i >= size; i--) {
  188.                 res += data[i] * pow(BASE, N - 1 - i - FL_P);
  189.             }
  190.             if (sign == -1) {
  191.                 res *= -1;
  192.             }
  193.             return res;
  194.         }
  195.  
  196.         InfNum operator + (InfNum &num) {
  197.             InfNum result = sum(*this, num);
  198.             result.updateSize();
  199.             return result;
  200.         }
  201.  
  202.         InfNum operator - (InfNum &num) {
  203.             InfNum result = diff(*this, num);
  204.             result.updateSize();
  205.             return result;
  206.         }
  207.  
  208.         InfNum operator * (InfNum &num) {
  209.             InfNum result = mult(*this, num);
  210.             return result;
  211.         }
  212.  
  213.         InfNum operator / (InfNum &num) {
  214.             InfNum result = div(*this, num);
  215.             result.updateSize();
  216.             result.sign = this -> sign * num.sign;
  217.             return result;
  218.         }
  219.        
  220.         InfNum sqrt_l() {
  221.             if (sign == -1) return zero();
  222.            
  223.             InfNum x, one_obj = one(), r = *this + one_obj;
  224.        
  225.             binarySearch(zero(), r, x, *this, x, mult);
  226.             return x;
  227.         }
  228.  
  229.         char in() {
  230.             string s;
  231.            
  232.             cin >> s;
  233.             set(s);
  234.             return ' ';
  235.         }
  236.  
  237.         void set(string s) {
  238.             *this = zero();
  239.  
  240.             int i = 0;
  241.  
  242.             if (s[0] == '-') {
  243.                 i++;
  244.                 sign = -1;
  245.             } else {
  246.                 sign = 1;
  247.             }
  248.            
  249.             int k = 0, iS = -1;
  250.             bool flag = false;
  251.            
  252.             for (int i = 0; i < s.size(); i++) {
  253.                 if (s[i] == '.') {
  254.                     flag = true;
  255.                     iS = i;
  256.                 }
  257.                 if (flag) {
  258.                     if (s[i] != '.') {
  259.                         k++;
  260.                         data[N - 1 - (FL_P - k)] = s[i] - '0';
  261.                     }
  262.                 }
  263.             }
  264.            
  265.             if (iS > -1)
  266.             s.erase(iS);
  267.            
  268.             int len = s.size();
  269.            
  270.             for (i; i < len; i++) {
  271.                 data[N - len + i - FL_P] = s[i] - '0';
  272.             }  
  273.             updateSize();
  274.         }
  275.  
  276.         char out() {
  277.             bool flag = false;
  278.            
  279.             if (sign == -1) {
  280.                 cout << "-";
  281.             }
  282.            
  283.             int iEnd = N - 1;
  284.                
  285.             while (data[iEnd] == 0 && iEnd > N - 1 - FL_P) {
  286.                 iEnd--;
  287.             }
  288.            
  289.             for (int i = min(size, N - 1 - FL_P); i <= iEnd; i++) {
  290.                 if (i == N - FL_P) {
  291.                     cout << ".";
  292.                 }
  293.                 if (data[i] != 0 || i == N - FL_P) {
  294.                     flag = true;
  295.                 }
  296.                 if (flag) {
  297.                     cout << data[i];
  298.                 }
  299.             }
  300.             if (!flag) {
  301.                 cout << "0";
  302.             }
  303.             return ' ';
  304.         }
  305. };
  306.  
  307. void test() {
  308.     cout << "Running test ..." << endl;
  309.    
  310.     InfNum a, b, one;
  311.  
  312.     one.set("1");
  313.     a.set("-999");
  314.  
  315.     for (int aInt = -999; aInt <= 999; aInt++, a = a + one) {
  316.         b.set("-999");
  317.         for (int bInt = -999; bInt <= 999; bInt++, b = b + one) {
  318.             assert(aInt + bInt== (a + b).toInt() && "+ error!");
  319.             assert(aInt - bInt == (a - b).toInt() && "- error!");  
  320.             assert(aInt  * bInt == (a * b).toInt() && "* error!");
  321.             if (bInt != 0) {
  322.                 assert(aInt / bInt == (a / b).toInt() && "/ error!");
  323.             }
  324.         }
  325.     }
  326.     cout << "Test passed!" << endl;
  327.     return;
  328. }
  329.  
  330. int main() {
  331.    
  332.     if (RUN_TEST) {
  333.         test();
  334.     }
  335.  
  336.     InfNum a, b, c;
  337.  
  338.     cout << "Enter num a: "; cout << a.in() << endl;
  339.    
  340.  
  341.     cout << "Enter num b: "; cout << b.in() << endl;
  342.  
  343.     c = a + b;
  344.  
  345.     cout << "a + b = "; cout << c.out() << endl;
  346.  
  347.     //
  348.  
  349.     c = a - b;
  350.  
  351.     cout << "a - b = "; cout << c.out() << endl;
  352.  
  353.     //
  354.  
  355.     c = a * b;
  356.  
  357.     cout << "a * b = "; cout << c.out() << endl;
  358.  
  359.     //
  360.  
  361.     c = a / b;
  362.  
  363.     cout << "a / b = "; cout << c.out() << endl;
  364.    
  365.     //
  366.    
  367.     c = a.sqrt_l();
  368.  
  369.     cout << "sqrt(a) = "; cout << c.out() << endl;
  370.    
  371.     c = b.sqrt_l();
  372.  
  373.     cout << "sqrt(b) = "; cout << c.out() << endl;
  374.  
  375.     return 0;
  376. }
Add Comment
Please, Sign In to add comment