Кажется, проблема с умножением и распределением новых значений multVact

#c #segmentation-fault #vertices

#c #ошибка сегментации #вершины

Вопрос:

Создаются два вектора, и обоим векторам присваиваются значения, а затем два вектора умножаются друг на друга. (Матричное умножение). Выдает ошибку ошибки сегментации в функции умножения. Это что-то связанное с попыткой получить доступ к местоположению вне области видимости?

 #include<iostream>
#include <vector>

using namespace std;

int n;
vector <int> mat1Rows;
vector <int> mat2Rows;
vector <int> multRows;
vector <vector<int> > mat1;
vector <vector<int> > mat2;
vector <vector<int> > multMat;

void assignValues(int num){

        for(int i = 0; i < num; i  ){
                for(int j = 0; j < num; j  ){
                        mat1Rows.push_back(j);
                        mat2Rows.push_back(j);
                }
                mat1.push_back(mat1Rows);
                mat2.push_back(mat2Rows);

        mat1Rows.clear();
        mat2Rows.clear();
        }
}

void multiply(int n){

        for(int i = 0; i < n;   i){
                for(int j = 0; j < n;   j){
                        for(int k = 0; k < n;   k){

                multMat[i][j]  = mat1[i][k] * mat2[k][j];
                        }
                }
    }
}

void displayMult(int n){

    for(int i = 0; i < n; i  ){
        for(int j = 0; j < n; j  ){

            cout << multMat[i][j] << " " ;
        }

        cout << endl;
    }

}

int main(){

    cout << "Enter the size of the matrix: ";
    cin >> n;

    assignValues(n);

    multiply(n);

    displayMult(n);

    return 0;   
}
 

Комментарии:

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

2. «Это что-то с попыткой получить доступ к местоположению вне области видимости?» — это в значительной степени то, что означает ошибка сегментации. Самый простой способ найти это — пошагово выполнить вашу программу построчно с помощью debugger.

3. @NO_NAME Добавил includes .

4. multMat вектор пуст в тот момент, когда вы пытаетесь получить ссылку на его элемент с multMat[i][j] помощью .

5. @Rashmika97 Используйте vector::at() вместо [ ] для доступа к элементам в векторе. Затем вы увидите, что программа будет выдавать std::out_of_range исключение вместо просто ошибки seg, когда она встречает at() вызов, который выходит за рамки.

Ответ №1:

  multMat[i][j]  = mat1[i][k] * mat2[k][j];
 

Внутри нет памяти multMat , так как вы не зарезервировали никакой памяти для элементов. Вам нужно указать vector для выделения памяти. Вы можете сделать это с помощью resize, чтобы выделить память для элементов и изменить размер вектора..

  void multiply(int n) {
       multMat.resize(n);
       for (autoamp;amp; i : multMat) {
             i.resize(n);
       }
       ... rest of the code ...
  }
 

Проверка std::vector::operator[] границ не выполняется. Поэтому, если вы укажете индекс за пределами допустимых границ и попытаетесь присвоить что-то возвращаемой ссылке, произойдет неопределенное поведение. Используйте std::vector::at() , чтобы всегда быть уверенным, что ваши индексы действительны.

Комментарии:

1. Кстати, reserve() размер вектора не изменяется.

2. Разве это не должно быть resize() вместо reserve() ? reserve() предотвратил бы ошибку сегментации, но доступ к полям за пределами size() вектора по-прежнему пахнет для меня неопределенным поведением.

3. Было бы целесообразно зарезервировать память, поскольку это динамическое распределение?

4. Он operator[] не выполняет никакого распределения. Он не выполняет никакой проверки. Использование его за пределами границ является неопределенным поведением.

5. Да, я согласен, что в случае вектора какого-то фундаментального типа это не имеет большого значения. Однако лучше знать, когда использовать resize() и когда reserve() . Это может вызвать довольно странную ошибку в векторе объектов с конструктором и деструктором. Кроме того, попытка использования push_back переопределила бы данные, если resize() resize() бы был вызван только if only .