0

Here is my code. As you see i use arrays s1, s2, .. etc for results. But when i change recursivly s1, s2, .. etc, it changes on all steps of the recursion. So as a result, the first s1 = the last s1. How to fix it? So that at each step of recursion there should be different values of s1, s2, etc. I know the problem is that I pass arrays into the functions by value, but idk how to fix it. Thanks (sry for my Eng :p )

#include "pch.h"
#include<iostream>
#include<cstdio>
#include<conio.h>
#include<cstdlib>
#include<cmath>
#include<ctime>
#include<clocale>
#include <iomanip>
using namespace std;

void vivod(int **matrix, int n);
int** Matrix_Add(int **a, int **b, int **c, int n, int x1, int y1, int x2, int y2);
int** Matrix_Sub(int **a, int **b, int **c, int n, int x1, int y1, int x2, int y2);
int** Matrix_Multiply(int **a, int **b, int **c, int x1, int y1, int x2, int y2, int n);
int** strassen(int  **a, int **b, int **c, int **s1, int **s2, int **s3, int **s4, int **s5, int **s6, int **s7, int **s8, int **m1, int **m2, int **m3, int **m4, int **m5, int **m6, int **m7, int **t1, int **t2, int** c11, int** c12, int** c21, int** c22, int m, int n, int x1, int y1, int x2, int y2);
int** Naive_Multiply(int  **a, int **b, int **c, int n);

int main()
{
    setlocale(LC_ALL, "Russian");
    int n;
    cout << "Enter the N:";
    cin >> n;
    int **A = new int*[n];
    int **B = new int*[n];
    int **C = new int*[n];
    int **k = new int*[n];
    int **s1 = new int*[n];
    int **s2 = new int*[n];
    int **s3 = new int*[n];
    int **s4 = new int*[n];
    int **s5 = new int*[n];
    int **s6 = new int*[n];
    int **s7 = new int*[n];
    int **s8 = new int*[n];
    int **m1 = new int*[n];
    int **m2 = new int*[n];
    int **m3 = new int*[n];
    int **m4 = new int*[n];
    int **m5 = new int*[n];
    int **m6 = new int*[n];
    int **m7 = new int*[n];
    int **t1 = new int*[n];
    int **t2 = new int*[n];
    int **c11 = new int*[n];
    int **c12 = new int*[n];
    int **c21 = new int*[n];
    int **c22 = new int*[n];
    int **buff = new int*[n];
    for (int i = 0; i < n; i++)
    {
        buff[i] = new int[n];
        A[i] = new int[n];
        B[i] = new int[n];
        C[i] = new int[n];
        k[i] = new int[n];
        s1[i] = new int[n];
        s2[i] = new int[n];
        s3[i] = new int[n];
        s4[i] = new int[n];
        s5[i] = new int[n];
        s6[i] = new int[n];
        s7[i] = new int[n];
        s8[i] = new int[n];
        m1[i] = new int[n];
        m2[i] = new int[n];
        m3[i] = new int[n];
        m4[i] = new int[n];
        m5[i] = new int[n];
        m6[i] = new int[n];
        m7[i] = new int[n];
        t1[i] = new int[n];
        t2[i] = new int[n];
        c11[i] = new int[n];
        c12[i] = new int[n];
        c21[i] = new int[n];
        c22[i] = new int[n];
    }
    for (int i = 0; i < n; i++)
        for (int j = 0; j < n; j++) {
            A[i][j] = rand() % 10;
            B[i][j] = rand() % 10;
        }
    cout << "First Matrix:" << endl;
    vivod(A, n);
    cout << "Second Matrix:" << endl;
    vivod(B, n);
    int begin = clock();
    //for (int i =0; i < 100; i++)
    k = Naive_Multiply(A, B, k, n);
    int end = clock();
    cout << "Naive Multiply tacts: " << end - begin << endl;
    vivod(k, n);
    int begin2 = clock();
    //for (int i = 0; i < 100; i++)
    C = strassen(A, B, C, s1, s2, s3, s4, s5, s6, s7, s8, m1, m2, m3, m4, m5, m6, m7, t1, t2, c11, c12, c21, c22, n, n, 0, 0, 0, 0);
    int end2 = clock();
    cout << "Shtrassen tacts: " << end2 - begin2 << endl;
    vivod(C, n);
    for (int i = 0; i < n; i++)
    {
        delete[] A[i];
        delete[] B[i];
        delete[] C[i];
        delete[] k[i];
        delete[] s1[i];
        delete[] s2[i];
        delete[] s3[i];
        delete[] s4[i];
        delete[] s5[i];
        delete[] s6[i];
        delete[] s7[i];
        delete[] s8[i];
        delete[] m1[i];
        delete[] m2[i];
        delete[] m3[i];
        delete[] m4[i];
        delete[] m5[i];
        delete[] m6[i];
        delete[] m7[i];
        delete[] t1[i];
        delete[] t2[i];
        delete[] c11[i];
        delete[] c12[i];
        delete[] c21[i];
        delete[] c22[i];
    }
    system("pause");
    return 0;
}
int** strassen(int  **a, int **b, int **c, int **s1, int **s2, int **s3, int **s4, int **s5, int **s6, int **s7, int **s8, int **m1, int **m2, int **m3, int **m4, int **m5, int **m6, int **m7, int **t1, int **t2, int** c11, int** c12, int** c21, int** c22, int m, int n, int x1, int y1, int x2, int y2) {
    m = n / 2;
    if (m != 1)
    {
        s1 = Matrix_Add(a, a, s1, m, x1 + m, y1, x1 + m, y1 + m);
        s2 = Matrix_Sub(s1, a, c, m, 0, 0, x1, y1);
        s3 = Matrix_Sub(a, a, s3, m, x1, y1, x1 + m, y1);
        s4 = Matrix_Sub(a, s2, s4, m, x1, y1 + m, 0, 0);
        s5 = Matrix_Sub(b, b, s5, m, x2, y2 + m, x2, y2);
        s6 = Matrix_Sub(b, s5, s6, m, x2 + m, y2 + m, 0, 0);
        s7 = Matrix_Sub(b, b, s7, m, x2 + m, y2 + m, x2, y2 + m);
        s8 = Matrix_Sub(s6, b, s8, m, 0, 0, x2 + m, y2);

        m1 = strassen(s2, s6, m1, s1, s2, s3, s4, s5, s6, s7, s8, m1, m2, m3, m4, m5, m6, m7, t1, t2, c11, c12, c21, c22, m, m, 0, 0, 0, 0);
        m2 = strassen(a, b, m2, s1, s2, s3, s4, s5, s6, s7, s8, m1, m2, m3, m4, m5, m6, m7, t1, t2, c11, c12, c21, c22, m, m, x1, y1, x2, y2);
        m3 = strassen(a, b, m3, s1, s2, s3, s4, s5, s6, s7, s8, m1, m2, m3, m4, m5, m6, m7, t1, t2, c11, c12, c21, c22, m, m, x1, y1 + m, x2 + m, y2);
        m4 = strassen(s3, s7, m4, s1, s2, s3, s4, s5, s6, s7, s8, m1, m2, m3, m4, m5, m6, m7, t1, t2, c11, c12, c21, c22, m, m, 0, 0, 0, 0);
        m5 = strassen(s1, s5, m5, s1, s2, s3, s4, s5, s6, s7, s8, m1, m2, m3, m4, m5, m6, m7, t1, t2, c11, c12, c21, c22, m, m, 0, 0, 0, 0);
        m6 = strassen(s4, b, m6, s1, s2, s3, s4, s5, s6, s7, s8, m1, m2, m3, m4, m5, m6, m7, t1, t2, c11, c12, c21, c22, m, m, 0, 0, x2 + m, y2 + m);
        m7 = strassen(a, b, m7, s1, s2, s3, s4, s5, s6, s7, s8, m1, m2, m3, m4, m5, m6, m7, t1, t2, c11, c12, c21, c22, m, m, x1 + m, y1 + m, 0, 0);

        t1 = Matrix_Add(m1, m2, t1, m, 0, 0, 0, 0);
        t2 = Matrix_Add(t1, m4, t2, m, 0, 0, 0, 0);

        c11 = Matrix_Add(m2, m3, c11, m, 0, 0, 0, 0);
        c21 = Matrix_Sub(t2, m7, c21, m, 0, 0, 0, 0);
        c12 = Matrix_Add(t1, m5, c12, m, 0, 0, 0, 0);
        c12 = Matrix_Add(c12, m6, c12, m, 0, 0, 0, 0);
        c22 = Matrix_Add(t2, m5, c22, m, 0, 0, 0, 0);
        for (int i = 0; i < n / 2; i++)
        {
            for (int j = 0; j < n / 2; j++)
            {
                c[i + n - 2 * m][j + n - 2 * m] = c11[i][j];
                c[i + n - 2 * m][j + n - m] = c12[i][j];
                c[i + n - m][j + n - 2 * m] = c21[i][j];
                c[i + n - m][j + n - m] = c22[i][j];
            }
        }
    }
    else
    {
        c = Matrix_Multiply(a, b, c, x1, y1, x2, y2, n);
    }
    return c;
}
void vivod(int **matrix, int n)
{
    for (int i = 0; i < n; i++)
    {
        for (int j = 0; j < n; j++)
        {
            cout << matrix[i][j] << " ";
        }
        cout << endl;
    }
    cout << endl;
}
int** Matrix_Add(int **a, int **b, int **c, int n, int x1, int y1, int x2, int y2)
{
    for (int i = 0; i < n; i++) {
        for (int j = 0; j < n; j++) {
            c[i][j] = a[i + x1][j + y1] + b[i + x2][j + y2];
        }
    }
    return c;
}

int** Matrix_Sub(int **a, int **b, int **c, int n, int x1, int y1, int x2, int y2)
{
    for (int i = 0; i < n; i++) {
        for (int j = 0; j < n; j++) {
            c[i][j] = a[i + x1][j + y1] - b[i + x2][j + y2];
        }
    }
    return c;
}
int** Matrix_Multiply(int **a, int **b, int **c, int x1, int y1, int x2, int y2, int n)
{
    for (int i = 0; i < n; i++) {
        for (int j = 0; j < n; j++) {
            c[i][j] = 0;
            for (int t = 0; t < n; t++) {
                c[i][j] = c[i][j] + a[x1 + i][y1 + t] * b[x2 + t][y2 + j];
            }
        }
    }
    return c;
}
int** Naive_Multiply(int **a, int **b, int **c, int n)
{
    for (int i = 0; i < n; i++) {
        for (int j = 0; j < n; j++) {
            c[i][j] = 0;
            for (int t = 0; t < n; t++) {
                c[i][j] = c[i][j] + a[i][t] * b[t][j];
            }
        }
    }
    return c;
}
Community
  • 1
  • 1
  • damn, here it is – NoActualName Dec 17 '18 at 15:22
  • 6
    Please provide a [mcve]. It is tough, but emphasis in *minimal*. Also, please fix the indentation. – AndyG Dec 17 '18 at 15:23
  • 1
    Using meaningless names for various variables, like `s1`, `s2`, `s-whatever` -- makes the resulting code completely unreadable and incomprehensible to everyone else but you. I'm sure there are specific meaning to all of these multidimensional arrays. Using meaningful variable names that describe those variables' intended purpose makes the resulting code more informative and understandable. You want to make your code easily understood by others, for a better chance that someone can see what the problem is. Try doing that. – Sam Varshavchik Dec 17 '18 at 15:29
  • 6
    When you write a recursive function *with over 30 arguments* it's very unlikely to work. I don't know what the problem is but passing 'arrays' by value is not it. You need to work on simplifying your code to have any chance of getting it to work. Rewriting your functions to only use the parameters they really need would be the first step. – john Dec 17 '18 at 15:30
  • 4
    You are not passing arrays to recursive calls - you are passing pointers. The callee has its own copy of the *pointer* distinct from that of the caller - but they both still point to the same data. You seem to believe that deep copies of actual numeric data occur at each recursive call; that's not what happens. – Igor Tandetnik Dec 17 '18 at 15:38
  • 2
    This code uses some features of C++, but this code is written in bad C style. – Marek R Dec 17 '18 at 16:10
  • For those wondering what this code is supposed to do, it is likely related to the OPs question about Strassen-matrix-products: https://stackoverflow.com/questions/53802871/strassen-vinograd-algorithm. That said, stackoverflow is not a "please review my 100-lines-of-code-function" service. As said before, reduce your problem to a [mcve]! – chtz Jan 11 '19 at 15:13

0 Answers0