#include <iostream>
#include <stdlib.h>
using namespace std;
float **div(float **A, float **B, int row, int column) {
float **D;
D = new float *[row];
// D= ( float **)malloc(sizeof(float *) * row);
for (int x = 0; x < row; x++) {
D[x] = new float[column];
// D[x] = (float (*))malloc(sizeof(float) * column);
for (int y = 0; y < column; y++) {
D[x][y] = (A[x][y] / B[x][y]);
}
}
return D;
}
int main() {
int x = 0, y = 0, row = 20, column = 5;
float **N;
// N =(float **)malloc(sizeof(float *) * row);
N = new float *[row];
for (x = 0; x < row; x++) {
N[x] = new float[column];
// N[x]=(float*)malloc(row*column*sizeof(float));
for (y = 0; y < (column); y++) {
N[x][y] = 1;
}
}
N = div(N, N, row, column);
cout << "Displaying N ..." << endl;
for (int x = 0; x < 10; x++) {
for (int y = 0; y < 5; y++) {
cout << N[x][y] << " ";
}
cout << endl;
}
for (int x = 0; x < 20; x++) {
delete[] N[x];
}
delete[] N;
return 0;
}
I am trying to free the all the memory, but it is freed the memory which I declared in main, but the function div also occupying the same memory of size input array N and it is not freed. Is there any way to delete the memory which is occupied the function.
Please look at here, my example of new and delete a int[m][n], I hope this can help you:
int main()
{
//a[m][n]
const int m = 5, n=6;
int **p = new int*[m];
for(int i=0; i<m; ++i)
p[i] = new int[n];
for(int i=0; i<m; ++i)
delete[] p[i]; //delete array
delete[] p;
p = nullptr;
}
Using std::array would remove memory management:
template <std::size_t ROW, std::size_t COL>
using Matrix = std::array<std::array<float, COL>, ROW>;
template <std::size_t ROW, std::size_t COL>
Matrix<ROW, COL> div(const Matrix<ROW, COL>& A, const Matrix<ROW, COL>& B)
{
Matrix<ROW, COL> res;
for (std::size_t x = 0; x != ROW; ++x) {
for (std::size_t y = 0; y != COL; ++y) {
res[x][y] = (A[x][y]/B[x][y]);
}
}
return res;
}
template <std::size_t ROW, std::size_t COL>
void display(const Matrix<ROW, COL>& m)
{
for (std::size_t x = 0; x != ROW; ++x) {
for (std::size_t y = 0; y != COL; ++y) {
std::cout << m[x][y] << " ";
}
std::cout << std::endl;
}
}
int main()
{
Matrix<20, 5> N;
for (std::size_t x = 0; x != 20; ++x) {
for (std::size_t y = 0; y != 5; ++y) {
N[x][y] = 1;
}
}
N = div(N, N);
std::cout << "Displaying N ..." << std::endl;
display(N);
}
Demo
Related
I'm trying to multiply 2 matrices together using operator-overloading but I'm getting an error when trying to convert my int array into my matrix class in order to use it. I'm not sure how to fix these errors
#include <iostream>
using namespace std;
struct matrix{
int array[4][4];
public:
void make(int A[][4], int size) {
for (int x = 0; x < size; x++) {
for (int y = 0; y < size; y++) {
array[x][y] = A[x][y];
}
}
}
void operator*(matrix m) {
int output[4][4];
for (int x = 0; x < 4; x++){
for (int y = 0; y < 4; y++){
array[x][y] = (array[x][y] * m.array[x][y]);
}
}
for (int x = 0; x < 4; x++) {
for (int y = 0; y < 4; y++) {
cout << output[x][y] << " ";
}
cout << endl;
}
}
};
int main(){
matrix m1, m2;
int a[4][4] = {{1,2,3,4},{5,6,7,8},{9,10,11,12},{13,14,15,16}};
//int c[3][3] = {{1,2,3},{4,5,6},{7,8,9}};
m1.make(a[4][4], 4);
m2.make(a[4][4], 4);
m1*m2;
return 0;
}
There are two problem with your code:-
m1.make(a[4][4], 4); // should be m1.make(a, 4); make is expecting a 2D array you are passing an integer
In the operator *function
array[x][y] = (array[x][y] * m.array[x][y]); // your should assign to output[x][y] here
You are not using the corect syntax.
int main(){
matrix m1, m2;
int a[4][4] = {{1,2,3,4},{5,6,7,8},{9,10,11,12},{13,14,15,16}};
//int c[3][3] = {{1,2,3},{4,5,6},{7,8,9}};
// these are not good, you try to pass a single int, and it is past the
// end of a.
//m1.make(a[4][4], 4);
//m2.make(a[4][4], 4);
// try this instead:
m1.make(a, 4);
m2.make(a, 4);
m1*m2;
return 0;
}
Multiplying is a binary operator that takes in 2 matrices, and outputs a third one with the result.
class matrix
{
// note the friend modifier, which indicates this fonction is a not a member
// of the class, and can access all of its private members.
friend matrix operator*(const matrix& m, const matrix& n)
{
matrix result;
for (int x = 0; x < 4; x++)
for (int y = 0; y < 4; y++)
result.array[x][y] = (m.array[x][y] * n.array[x][y]);
// your formula does not seem quite right here...
// I'll let you fix it.
return result;
}
Here is the correct syntax for make() to accept an int[4][4] array:
void make(int (&A)[4][4]) {
for (int x = 0; x < 4; x++) {
for (int y = 0; y < 4; y++) {
array[x][y] = A[x][y];
}
}
}
Why don't you have a constructor instead of make?
class matrix{
private:
int array[4][4];
public:
// you want to initialize your data, always (well, almost always, but
// this is the kind of data that always applies to)...
matrix()
{
for (int x = 0; x < 4; x++)
for (int y = 0; y < 4; y++)
array[x][y] = 0;
}
explicit matrix(const int(&a)[4][4])
{
for (int x = 0; x < 4; x++)
for (int y = 0; y < 4; y++)
array[x][y] = a[x][y];
}
matrix& operator=(const int(&a)[4][4])
{
return *this = matrix(a);
}
matrix& operator=(const matrix& m)
{
for (int x = 0; x < 4; x++)
for (int y = 0; y < 4; y++)
array[x][y] = m.array[x][y];
return *this;
}
// ...
};
Then main() becomes:
int main(){
matrix m1, m2;
int a[4][4] = {{1,2,3,4},{5,6,7,8},{9,10,11,12},{13,14,15,16}};
matrix m1(a);
matrix m2(a);
matrix product = m1 * m2;
return 0;
}
I have a function "mod_kadane" defined in class "MAX_SUB_MAT" which returns an object.
#define dx 101
class MAX_SUB_MAT
{
public:
int curr_sum, max_sum, left, right, up, down;
MAX_SUB_MAT mod_kadane(int mat[dx][dx], int row, int column)
{
MAX_SUB_MAT objx;
curr_sum = objx.max_sum = INT_MIN;
int sub_mat[row];
for(int L = 0; L < row; L++)
{
memset(sub_mat, 0, sizeof sub_mat);
for(int R = L; R < column; R++)
{
for(int i = 0; i < row; i++)
{
sub_mat[i] += i;//mat[i][R];
}
MAX_SUB_ARR obj;
obj = obj.kadane(sub_mat, row);
curr_sum = obj.maxima;
if(curr_sum > objx.max_sum)
{
objx.max_sum = curr_sum;
objx.left = L;
objx.right = R;
objx.up = obj.left;
objx.down = obj.right;
}
}
}
return objx;
}
};
But when I'm trying to call it from "main":
cin >> row >> column;
int mat[row][column];
for(int i = 0; i < row; i++)
{
for(int j = 0; j < column; j++)
{
cin >> mat[i][j];
}
}
MAX_SUB_MAT objx;
objx = objx.mod_kadane(mat, row, column);
then an error is shown:
error: no matching function for call to 'MAX_SUB_MAT::mod_kadane(int [row][column], int&, int&)'|
But if I remove the 2d array "mat" from both sides then the code works fine.
Here is my full code:
#include<bits/stdc++.h>
#define dx 101
using namespace std;
class MAX_SUB_ARR
{
public:
int max_curr, maxima, left, right;
MAX_SUB_ARR kadane(int arr[], int n)
{
MAX_SUB_ARR obj;
obj.maxima = max_curr = INT_MIN;
//cout << obj.maxima << endl;
/*for(int i = 0; i < n; i++)
cout << arr[i] << endl;*/
for(int i = 0; i < n; i++)
{
if(max_curr < 0)
{
max_curr = arr[i];
obj.left = i;
}
else
{
max_curr += arr[i];
}
//maxima = max(maxima, max_curr);
if(max_curr > obj.maxima)
{
obj.maxima = max_curr;
obj.right = i;
//cout << obj.maxima << endl;
}
}
return obj;
}
};
class MAX_SUB_MAT
{
public:
int curr_sum, max_sum, left, right, up, down;
/* MAX_SUB_MAT(int r, int c)
{
row = r;
column = c;
}*/
MAX_SUB_MAT mod_kadane(int mat[dx][dx], int row, int column)
{
MAX_SUB_MAT objx;
curr_sum = objx.max_sum = INT_MIN;
int sub_mat[row];
for(int L = 0; L < row; L++)
{
memset(sub_mat, 0, sizeof sub_mat);
for(int R = L; R < column; R++)
{
for(int i = 0; i < row; i++)
{
sub_mat[i] += i;//mat[i][R];
}
MAX_SUB_ARR obj;
obj = obj.kadane(sub_mat, row);
curr_sum = obj.maxima;
if(curr_sum > objx.max_sum)
{
objx.max_sum = curr_sum;
objx.left = L;
objx.right = R;
objx.up = obj.left;
objx.down = obj.right;
}
}
}
return objx;
}
};
int main()
{
int row, column;
printf("Number of rows you want to insert?:\n");
cin >> row;
printf("Number of columns you want to insert?:\n");
cin >> column;
int mat[row][column];
if(row && column)
{
for(int i = 0; i < row; i++)
{
for(int j = 0; j < column; j++)
{
cin >> mat[i][j];
}
}
//int curr_sum, max_sum, left, right, up, down;
//MAX_SUB_MAT objx = new MAX_SUB_MAT(row, column);
MAX_SUB_MAT objx;
objx = objx.mod_kadane(mat, row, column);
for(int i = objx.up; i <= objx.down; i++)
{
for(int j = objx.left; j <= objx.right; j++)
{
cout << mat[i][j] << " ";
}
cout << endl;
}
}
return 0;
}
It is not true that in C or C++ we cannot declare a function with two dimensional array parameter with both sizes specified.
See: http://c-faq.com/aryptr/pass2dary.html
The problem has been correctly explained by #AlanStokes in his comments!
I have a University assignment whereby I have a 1D array, containing 262144 values. I've created a matrix class which places these values into an object with the datasource being the double* list of 262144 values.
I need to be able to obtain a sub-matrix (which I'm able to do) from ANOTHER set of 262144 values (which I've also placed into a matrix object).
However, I'm having serious trouble and I've been trying so hard for the last 3 days to try and replace original matrix values from a sub-matrix. I've tried passing by reference, creating Matrix*'s. I've tried everything we've been taught and even researched a few more methods, all of which I haven't understood. I'll throw my code in here to see if anyone can explain a method to me which will be able to do this.
Matrix::Matrix()
{
"Matrix::Matrix() is invoked";
}
Matrix::Matrix(const Matrix& m)
{
"Matrix::Matrix(const Matrix&) is invoked";
_M = m._M;
_N = m._N;
_data = new double[_M*_N];
for (int i = 0; i < _M*_N; i++)
{
_data[i] = m._data[i];
}
}
Matrix::Matrix(int sizeR, int sizeC, double *input_data)
{
"Matrix::Matrix(int sizeR, int sizeC, double *input_data is invoked";
_M = sizeR;
_N = sizeC;
_data = new double[_M*_N];
for (int i = 0; i < _M*_N; i++)
{
_data[i] = input_data[i];
}
}
Matrix Matrix::get_Block(int start_row, int end_row, int start_coloumn, int end_coloumn)
{
int rows = (end_row - start_row);
int columns = (end_coloumn - start_coloumn);
int ctr = 0;
double *temp_Data = new double[rows*columns];
for (int x = start_row; x < (rows + start_row); x++)
{
for (int y = start_coloumn; y < (columns + start_coloumn); y++)
{
temp_Data[ctr] = get(x, y);
ctr++;
}
}
Matrix block(rows, columns, temp_Data);
delete[] temp_Data;
return block;
}
Matrix Matrix::operator+(const Matrix & other)
{
Matrix temp;
temp._M = other._M;
temp._N = other._N;
temp._data = new double[temp._M*temp._N];
for (int x = 0; x < (temp._M*temp._N); x++)
{
temp._data[x] = this->_data[x] + other._data[x];
}
return temp;
}
Matrix Matrix::operator*(const Matrix & other)
{
Matrix temp;
temp._M = other._M;
temp._N = other._N;
temp._data = new double[temp._M*temp._N];
for (int x = 0; x < (temp._M*temp._N); x++)
{
temp._data[x] = this->_data[x] * other._data[x];
}
return temp;
}
Matrix Matrix::operator-(const Matrix & other)
{
Matrix temp;
temp._M = other._M;
temp._N = other._N;
temp._data = new double[temp._M*temp._N];
for (int x = 0; x < (temp._M*temp._N); x++)
{
temp._data[x] = this->_data[x] - other._data[x];
}
return temp;
}
void Matrix::replace_Block(Matrix& noisy, Matrix& shuffled,int k, int j, int i)
{
int val_to_replace = 0;
for (int i = 0; i < 3 * 3; i++)
{
val_to_replace = shuffled.get(i, j);
noisy.set(i, j, val_to_replace);
}
}
void Matrix::set_Block(Matrix block, Matrix& Noisy, int start_row, int end_row)
{
int ctr = 0;
int ctr2 = 0;
int ctr3 = 0;
for (int i = 0; i < 3; i++)
{
Noisy._data[(start_row*_M)+i+4] = block.get(i, ctr);
ctr++;
}
for (int j = 0; j < 3; j++)
{
Noisy._data[((start_row + 1)*_M) + j + 3] = block.get(j, ctr2);
ctr2++;
}
for (int j = 0; j < 3; j++)
{
Noisy._data[((start_row + 1)*_M) + j + 2] = block.get(j, ctr3);
ctr3++;
}
}
double Matrix::get_Sum(Matrix m)
{
double total = 0;
short row = m.get_M();
short column = m.get_N();
for (int j = 0; j < row; j++)
{
for (int i = 0; i < column; i++)
{
total += m.get(j,i);
}
}
return total;
}
double Matrix::get_Sum(Matrix* m)
{
double total = 0;
short row = m->get_M();
short column = m->get_N();
for (int j = 0; j < row; j++)
{
for (int i = 0; i < column; i++)
{
total += m->get(i, j);
}
}
return total;
}
double Matrix::get(int i, int j)
{
return _data[(i * _M) + j];
}
void Matrix::write_Block(int i, int j)
{
for (int ctr = 0; ctr < i; ctr++)
{
for (int ctr2 = 0; ctr2 < j; ctr2++)
{
std::cout << " " << this->get(ctr,ctr2);
}
std::cout << std::endl;
}
}
void Matrix::set(int i, int j, double val)
{
this->_data[(i*_M) + j] = val;
}
void Matrix::set_N(int N)
{
_N = N;
}
void Matrix::set_M(int M)
{
_M = M;
}
int Matrix::get_N()
{
return _N;
}
int Matrix::get_M()
{
return _M;
}
Matrix::~Matrix()
{
"Matrix::~Matrix() is invoked";
delete[] _data;
}
If it would be helpful to see main() I can supply that too, however all it really contains is the creation of the matrix objects using overloaded constructors.
explanation
Answer is only 4 years late . . .
Anyway. Maybe it will help somebody else. The secret is to use a std::valarray. With that it is utmost simple to work on a matrix. And, many many functions are available.
All the functions that you want to implement are already available.
And you sub-matrix coy can be a one liner . . .
Please see example code:
#include <iostream>
#include <algorithm>
#include <numeric>
#include <valarray>
#include <iomanip>
constexpr size_t NRows = 6;
constexpr size_t NCols = 8;
constexpr size_t SubNRows = 2;
constexpr size_t SubNCols = 3;
void debugPrint(std::valarray<int> &v, size_t nrows = NRows, size_t ncols = NCols)
{
for (int r = 0; r < nrows; ++r) {
for (int c = 0; c < ncols; ++c)
std::cout << std::setw(3) << v[r*ncols+c] << ' ';
std::cout << '\n';
}
std::cout << '\n';
}
int main()
{
std::valarray<int> v1(NRows * NCols); // Define array with given size
std::iota(std::begin(v1),std::end(v1),0); // Fill the array with consecutive nunbers
debugPrint (v1); // Print the result
std::cout << "\nSum = " << v1.sum() << "\n\n"; // Print the sum of all values in matrix
std::valarray<int> v2(v1); // Create a 2nd matrix as a copy to the first
v2 += 100; // Add 100 to each value in the matrix
debugPrint(v2);
std::valarray<int> v3(NCols); // Get one column
v3 = v1[std::slice(2,NRows,NCols)];
debugPrint(v3,NRows,1);
std::valarray<int> subV2(SubNRows*SubNCols); // So, now the sub array
subV2 = v2[std::gslice(12,{SubNRows, SubNCols},{NCols,1})]; // Slice it out
debugPrint(subV2, SubNRows, SubNCols);
v1[std::gslice(25,{SubNRows, SubNCols},{NCols,1})] = subV2; // And copy to the first array
debugPrint (v1);
return 0;
}
I'm trying to return a sub-image from a 5x7 matrix. I'm trying to retrieve the sub matrix (0,2,0,2). I've created a function get_Block which SHOULD return the values of the matrix to temp, however just getting:
Exception thrown at 0x003B2A96 in Logo_Unscrambler.exe: 0xC0000005: Access violation reading location 0xCCCCCCCC.
It's probably super simple but I'm mega tired and I can't see it. Here's the code:
Main:
int main() {
double* A = new double[5*7];
for (int i = 0; i < 5 * 7; i++)
{
A[i] = i;
}
Matrix Ab(5, 7, A);
Matrix temp;
temp = Ab.get_Block(0, 2, 0, 2);
for (int k = 0; k < 3; k++)
{
for (int i = 0; i < 3; i++)
{
cout << " " << temp.get(k,i, 3);
}
cout << endl;
}
system("pause");
return 0;
}
Matrix.cpp:
Matrix::Matrix(int sizeR, int sizeC, double *input_data)
{
"Matrix::Matrix(int sizeR, int sizeC, double *input_data is invoked";
_M = sizeR;
_N = sizeC;
_data = new double[_M*_N];
for (int i = 0; i < _M*_N; i++)
{
_data[i] = input_data[i];
}
}
Matrix Matrix::get_Block(int start_row, int end_row, int start_coloumn, int end_coloumn)
{
int rows = (end_row - start_row) + 1;
int columns = (end_coloumn - start_coloumn) + 1;
int ctr = 0;
double *temp_Data = new double[rows*columns];
for (int x = start_row; x < (rows + start_row); x++)
{
for (int y = start_coloumn; y < (columns + start_coloumn); y++)
{
temp_Data[ctr] = get(x, y,rows);
ctr++;
}
}
Matrix block(rows, columns, temp_Data);
delete[] temp_Data;
return block;
}
double Matrix::get(int i, int j, int row_Count)
{
return _data[(i*_N) + j];
}
I wrote a function that reads an Image (2-d array) from a file and returns it.
Calling it gave me a Block-Type error, which I could suppress by removing the destructor.
Where is my error? Do I even need a destructor?
#include <vector>
#include <stdio.h>
#include <conio.h>
#include <iostream>
#include <fstream>
using namespace std;
struct Pixel {
float p;
};
class Image {
int _x, _y;
Pixel *pix;
public:
Image(int x, int y) {
pix = new Pixel[x * y];
_x = x;
_y = y;
}
~Image() {
delete[] pix;
pix = NULL;
}
Image& operator= (const Image& param) {
_x = param._x;
_y = param._y;
pix = new Pixel[_x*_y];
pix = param.pix;
return *this;
}
float getPixel(int i, int j) {
return pix[(i-1) * _y + (j-1)].p;
}
void setPixel(int i,int j, Pixel val) {
pix[(i-1) * _y + j-1].p = val.p;
}
Pixel **GetData() {
Pixel **a=0;
a = new Pixel*[_x];
for (int i = 0; i < _x; i++) {
a[i] = new Pixel[_y];
for (int j = 0; j < _y; j++)
a[i][j] = pix[i*_y + j];
}
return a;
}
};
Image ReadFromFile(string a) {
FILE * pFile;
const char * c = a.c_str();
Pixel pix,**tval;
int n,m;
pFile=fopen(c,"r");
fscanf(pFile, "%i %i", &n, &m);
Image img(n, m);
for (int i = 1; i <= n; i++)
for (int j = 1; j <= m; j++) {
fscanf(pFile, "%f", &pix.p);
img.setPixel(i, j, pix);
}
fclose(pFile);
return img;
}
int main(){
// Example Usage
Image img(10, 10);
Image img2(3, 3);
Pixel val[10][10], **tval;
for (int row = 1; row <= 10; row++)
for (int col = 1; col <= 10; col++) {
val[row-1][col-1].p = 2*row + col;
img.setPixel(row, col, val[row-1][col-1]);
}
for (int row = 1; row <= 10; row++) {
for (int col = 1; col <= 10; col++)
cout << img.getPixel(row,col) << ' ';
cout << '\n';
}
cout << '\n';
tval = img.GetData();
for (int row = 0; row < 10; row++) {
for (int col = 0; col < 10; col++)
cout << tval[row][col].p << ' ';
cout << '\n';
}
string a;
a = "C:/programs/misha/out.txt";
img2 = ReadFromFile(a);
cout << '\n';
for (int row = 0; row < 3; row++) {
for (int col = 0; col < 3; col++)
cout << img2.getPixel(row+1, col+1) << ' ';
cout << '\n';
}
}