Транспонирование матрицы с динамическим выделением памяти
Пишу прогу по транспонированию матрицы. После написания алгоритма, решил также выделить память динамически. Сделал. Но чета ломается прога в случае, когда num_of_rows не равно num_of_cols. И есть подозрение, что оператор присвоения тоже написан неверно, так как впервые делал это для двумерного массива. Без выделения памяти все работает! Укажите, пожалуйста, на ошибку.
Код с выделенной памятью:
#include <iostream>
using namespace std;
class Transpose{
int cols, rows, **data;
public:
Transpose(int arows, int acols){
cols = acols;
rows = arows;
data = new int *[rows];
for (int i = 0; i < rows; i++)
data[i] = new int[cols];
}
~Transpose(){
for (int i = 0; i < rows; i++) {
delete[] data[i];
}
delete[] data;
}
void scan(){
cout<<"Vvedite "<<cols * rows<<" cifri\n";
for(int i=0; i< rows; i++){
for(int j=0; j< cols; j++){
cin>>data[i][j];}
}
cout << endl;
}
void display()
{
for(int i=0; i< rows; i++){
for(int j=0; j< cols; j++){
cout<<data[i][j]<<" ";}
cout << "\n";
}
cout<< endl;
}
void print()
{
for(int i=0; i< cols; i++){
for(int j=0; j< rows; j++){
cout<<data[i][j]<<" ";}
cout << "\n";
}
cout << endl;
}
Transpose(const Transpose &ob)
{
rows=ob.rows;
cols=ob.cols;
data = new int *[rows];
for (int i = 0; i < rows; i++)
data[i] = new int[cols];
for(int i=0;i<rows;i++){
for(int j=0;j<cols;j++){
data[i][j]=ob.data[i][j];
}
}
}
Transpose transpose(){
Transpose temp(rows,cols);
for (int i = 0; i < rows; i++) {
for (int j = 0; j < cols; j++) {
temp.data[j][i] = data[i][j];
}
}
return temp;}
Transpose& operator=(const Transpose& ob)
{
if (this == &ob)
return *this;
if (data) delete[] data;
rows=ob.rows;
cols=ob.cols;
data = new int *[rows];
for (int i = 0; i < rows; i++)
data[i] = new int[cols];
for(int i=0;i<rows;i++){
for(int j=0;j<cols;j++){
data[i][j]=ob.data[i][j];
}
}
return *this;
}
};
int main(){
int num_of_cols, num_of_rows;
cout <<"input the num of cols and rows"<<endl;
cin >> num_of_rows >> num_of_cols;
Transpose ob1(num_of_rows, num_of_cols), ob2(num_of_cols, num_of_rows);
ob1.scan(); ob1.display();
ob2 = ob1.transpose();
ob2.print();
}
Код без выделения:
#include <iostream>
using namespace std;
class Transpose{
int cols, rows, data[10][10];
public:
Transpose(int arows, int acols){
cols = acols;
rows = arows;
}
void scan(){
cout<<"Vvedite "<<cols * rows<<" cifri\n";
for(int i=0; i< rows; i++){
for(int j=0; j< cols; j++){
cin>>data[i][j];}
}
cout << endl;
}
void display()
{
for(int i=0; i< rows; i++){
for(int j=0; j< cols; j++){
cout<<data[i][j]<<" ";}
cout << "\n";
}
cout<< endl;
}
void print()
{
for(int i=0; i< cols; i++){
for(int j=0; j< rows; j++){
cout<<data[i][j]<<" ";}
cout << "\n";
}
cout << endl;
}
Transpose transpose(){
Transpose temp(rows,cols);
for (int i = 0; i < rows; i++) {
for (int j = 0; j < cols; j++) {
temp.data[j][i] = data[i][j];
}
}
return temp;}
};
int main(){
int num_of_cols, num_of_rows;
cout <<"input the num of cols and rows"<<endl;
cin >> num_of_rows >> num_of_cols;
Transpose ob1(num_of_rows, num_of_cols), ob2(num_of_cols, num_of_rows);
ob1.scan(); ob1.display();
ob2 = ob1.transpose();
ob2.print();
}
Ответы (1 шт):
Вы выделяете точное количество памяти. А потом при транспонировании
Transpose transpose(){
Transpose temp(rows,cols);
for (int i = 0; i < rows; i++) {
for (int j = 0; j < cols; j++) {
temp.data[j][i] = data[i][j];
}
создаете такую же матрицу, в которой rows строк по cols элементов, но пишете в нее cols строк по rows элементов, неизбежно выходя за рамки выделенной памяти при rows != cols!
Да и, кстати, у вас оператор присваивания написан не совсем верно, с утечкой памяти, а конструктора копирования и вовсе нет, так что даже после того как вы исправите transpose(), все источники неприятностей не иссякнут...
Update
Вот как бы это делал я...
#include <iostream>
#include <iomanip>
using namespace std;
class Matrix
{
size_t rows, cols;
int **data;
void swap(Matrix&M)
{
std::swap(data,M.data);
std::swap(rows,M.rows);
std::swap(cols,M.cols);
}
public:
Matrix(size_t rows, size_t cols):rows(rows),cols(cols)
{
data = new int *[rows];
for(size_t i = 0; i < rows; i++)
data[i] = new int[cols];
}
~Matrix()
{
for (size_t i = 0; i < rows; i++)
delete[] data[i];
delete[] data;
}
Matrix(const Matrix&M):Matrix(M.rows,M.cols)
{
for(size_t i = 0; i < rows; i++)
for(size_t j = 0; j < cols; j++)
data[i][j] = M.data[i][j];
}
Matrix& operator = (const Matrix& M)
{
Matrix tmp(M);
swap(tmp);
return *this;
}
friend ostream& operator<<(ostream&os, const Matrix& M);
friend istream& operator>>(istream&is, Matrix& M);
Matrix transpose()
{
Matrix temp(cols,rows);
for(size_t i = 0; i < rows; i++)
for(size_t j = 0; j < cols; j++)
temp.data[j][i] = data[i][j];
return temp;
}
};
ostream& operator<<(ostream&os, const Matrix& M)
{
for(size_t i = 0; i < M.rows; i++)
{
for(size_t j = 0; j < M.cols; j++)
{
os << M.data[i][j]<< " ";
}
os << "\n";
}
return os;
}
istream& operator>>(istream&is, Matrix& M)
{
for(size_t i = 0; i < M.rows; i++)
{
for(size_t j = 0; j < M.cols; j++)
{
cout << "Matrix[" << i << "][" << j << "] = ";
is >> M.data[i][j];
}
}
return is;
}
int main()
{
int num_of_cols, num_of_rows;
cout <<"input the num of cols and rows"<<endl;
cin >> num_of_rows >> num_of_cols;
Matrix ob1(num_of_rows, num_of_cols);
cin >> ob1;
cout << "\n\n" << ob1 << "\n\n";
Matrix ob2 = ob1.transpose();
cout << ob2 << "\n\n";
}