I want to delete a consecutive row in a matrix. For example:
My matrix has 3 rows and 3 columns.
Elements of the matrix would be:
1 2 3
1 2 3
4 5 6
For this example the output should be:
1 2 3
4 5 6
I've tried an implementation but I have some problem, I know that I must use another matrix whose rows must be modified but I don't have any correct results till now.
How can I make it work?
#include <stdio.h>
#include <stdlib.h>
void readMatrix(int matrix[100][100], int noRows, int noCol);
void removeLine(int matrix[100][100], int noRows, int noCol);
void printMatrix(int matrix[100][100], int noRows, int noCol);
int main()
{
int noRows, noCol, matrix[100][100], i, j;
printf("n="); scanf("%d", &noRows);
printf("m="); scanf("%d", &noCol);
readMatrix(matrix, noRows, noCol);
printMatrix(matrix, noRows, noCol);
return 0;
}
void removeLine(int matrix[100][100], int noRows, int noCol)
{
int i, j;
int temp[100][100];
for (i = 0; i < noRows - 1; i++)
for (j = 0; j < noCol; j++)
{
if (matrix[i][j] == temp[i + 1][j])
{
matrix[i][j] == temp[i + 1][j];
}
}
}
void readMatrix(int matrix[100][100], int noRows, int noCol)
{
int i, j;
for (i = 0; i < noRows; i++)
for (j = 0; j < noCol; j++)
{
printf("\na[%d][%d]=", i, j); scanf("%d", &matrix[i][j]);
}
}
void printMatrix(int matrix[100][100], int noRows, int noCol)
{
int i, j;
for (i = 0; i < noRows; i++)
{
for (j = 0; j < noCol; j++)
{
printf("%d ", matrix[i][j]);
}
printf("\n");
}
}
You can't remove rows from the 2d array. You can shift rows to the left:
// Helper function to "delete" one row from the array
void deleteRow(int matrix[100][100], int row, int noRows, int noCol)
{
// Copy all rows after row to one row over
for (int i = row; i < noRows - 1; i++) {
// Use memcpy to copy entire row
memcpy(matrix[i], matrix[i+1], sizeof(int) * noCol);
}
}
// Remove repeats
void removeLines(int matrix[100][100], int *noRows, int noCol)
{
for (int i = 0; i < *noRows - 1; i++) {
// Use memcmp to compare entire row
if (memcmp(matrix[i], matrix[i + 1], sizeof(int) * noCol) == 0) {
deleteRow(matrix, i+1, *noRows, noCol);
i -= 1;
*noRows -= 1;
}
}
}
There is room for optimization here - especially when there are more than 1 repeats.
Related
I'm trying to write an iterative function that computes all the permutations of an array of numbers given in input.
Here is the code I've written so far.
void permute(int *a, int size){
int j=0, i, h=0, m;
bool flag=true;
int f = factorial(size);
int *arr, *res;
int counter=0;
arr = malloc(f*sizeof(int));
for(i=0; i<f; i++)
arr[i] = 0;
while (j < f) {
if(arr[j]<j)
{
if(j%2 == 0)
{
swap(a[0],a[j]);
} else {
swap(a[arr[j]], a[j]);
}
arr[j]++;
j=0;
} else{
arr[j] = 0;
j++;
}
printf("%d\n",a[j] );
}
}
The code doesn't compute well all the permutations and goes into a long loop. Can someone help me, please? Thanks to everyone.
Your code is close but includes some problems. For instance, the while loop
while (j < f) will assign j to a value out of bound of the array a.
Instead would you please try:
#include <stdio.h>
#include <stdlib.h>
int factorial(int x)
{
int i;
int y = 1;
for (i = 1; i <= x; i++) {
y *= i;
}
return y;
}
void swap(int *x, int *y)
{
int temp;
temp = *x;
*x = *y;
*y = temp;
}
void permute(int *a, int size)
{
int i, j = 0;
int f = factorial(size);
int *arr;
arr = calloc(f, sizeof(int)); // the members are initialized to 0
// print the original array
for (i = 0; i < size; i++) {
printf("%d%s", a[i], i == size - 1 ? "\n" : " ");
}
while (j < size) {
if (arr[j] < j) {
if (j % 2 == 0) {
swap(a + 0, a + j);
} else {
swap(a + arr[j], a + j);
}
// print the rearranged array
for (i = 0; i < size; i++) {
printf("%d%s", a[i], i == size - 1 ? "\n" : " ");
}
arr[j]++;
j = 0;
} else {
arr[j] = 0;
j++;
}
}
free(arr);
}
int main()
{
int a[] = {1, 2, 3}; // example
permute(a, sizeof a / sizeof a[0]); // the 2nd argument is the array length
return 0;
}
Output of the example:
1 2 3
2 1 3
3 1 2
1 3 2
2 3 1
3 2 1
In the matrix. c I have
struct matrix{
int row;
int col;
int *a;
};
Matrix* allocateMemory(int m, int n) {
Matrix* mat = (Matrix*) malloc(sizeof(Matrix));
if (mat == NULL) {
return NULL;
}
mat->row = m;
mat->col = n;
mat->a = (int*)calloc(m*n, sizeof(int));
return m;
}
While in the matrix.h I have
#ifndef MATRIX_H_INCLUDED
#define MATRIX_H_INCLUDED
typedef struct matrix Matrix;
Matrix* allocateMemory(int m, int n);
//...
int printMatrix(Matrix* mat);
int transpose(Matrix* mat);
#endif // MATRIX_H_INCLUDED
I am working in an ADT for matrices but I stucked in the print function. I would like to create a function
int printMatrix(Matrix* mat)
So in the main.c I would have something like
int i, j;
for (i = 0; i < row; i++){
for(j = 0; j < col; j++){
printf("%d ", printMatrix(mat));
}
printf("\n");
}
It means I want the printf in the main, not in the function, but I just could do this
void printMatrix(Matrix* mat){
int i, j, k;
for (i = 0; i < mat->row; i++){
for(j = 0; j < mat->col; j++){
k = i*mat->col + j;
printf("%d ", mat->a[k]);
}
printf("\n");
}
}
It does print the matrix, but it doesn't seem to be right. It is the same for the transpose matrix function, it does print the transpose matrix correctly, but I would like an
int transpose(Matrix* mat)
So I would use the function printMatrix in the main to print the transpose, but I just could do
void transpose(Matrix* mat){
int i, j, k;
for (i = 0; i < mat->col; i++){
for (j = 0; j < mat->row; j++){
k = j*mat->row + i;
printf("%f ", mat->a[k]);
}
printf("\n");
}
}
How can I create the int function to print the matrix?
I am still studying ADT, but what would be my lack of understanding so I couldn't do the function?
This is prefaced by my top comments.
A few more style tips ...
Do not cast the return of malloc [et. al.]
A bit more idiomatic is (e.g.):
Matrix *mat = malloc(sizeof(*mat));
I realize that in school, they teach the use of (e.g.) i, j, k, but try to use more descriptive names (e.g) row, col, off.
And, make the arguments descriptive as well:
Matrix *allocateMemory(int row,int col)
Here's a refactored version [with some style cleanups]:
#include <stdio.h>
#include <stdlib.h>
typedef struct matrix {
int row;
int col;
int *a;
} Matrix;
Matrix *
allocateMemory(int row, int col)
{
Matrix *mat = malloc(sizeof(*mat));
if (mat == NULL) {
perror("malloc");
exit(1);
}
mat->row = row;
mat->col = col;
mat->a = calloc(row * col, sizeof(*mat->a));
if (mat->a == NULL) {
perror("calloc");
exit(1);
}
return mat;
}
void
printMatrix(Matrix *mat)
{
int row, col, off;
for (row = 0; row < mat->row; row++) {
for (col = 0; col < mat->col; col++) {
off = (row * mat->col) + col;
printf("%d ", mat->a[off]);
}
printf("\n");
}
}
void
matrix_fill(Matrix * mat)
{
int row, col, off;
int val = 1;
for (row = 0; row < mat->row; row++) {
for (col = 0; col < mat->col; col++) {
off = (row * mat->col) + col;
mat->a[off] = val++;
}
}
}
void
transpose_copy(Matrix *matout,Matrix *matin)
{
int row, col;
int inoff, outoff;
for (row = 0; row < matin->row; row++) {
for (col = 0; col < matin->col; col++) {
inoff = (row * matin->col) + col;
outoff = (col * matout->col) + row;
matout->a[outoff] = matin->a[inoff];
}
printf("\n");
}
}
Matrix *
transpose_new(Matrix *matin)
{
Matrix *matout = allocateMemory(matin->col,matin->row);
transpose_copy(matout,matin);
return matout;
}
int
main(void)
{
Matrix *matin = allocateMemory(2,3);
matrix_fill(matin);
printf("Original:\n");
printMatrix(matin);
Matrix *matout = transpose_new(matin);
printf("Transposed:\n");
printMatrix(matout);
return 0;
}
Here's the program output:
Original:
1 2 3
4 5 6
Transposed:
1 4
2 5
3 6
The objective: Add only the pieces of the matrix that are part of a full X (upper and lower triangle).
1 1 1
0 1 0
1 1 1
Like this, middle one should add only once.
I can't add the lower triangle properly. Help much appreciated :)
void write(int niz[20][20], int n){
int i, j;
for(i=0; i<n; i++){
for(j=0; j<n; j++){
scanf("%d", &niz[i][j]);
}
}
}
void x(int niz[20][20], int n){
//Upper triangle
int i, j, pr=n, suma=0;
for(i=0; i<n/2 + n%2; i++,pr--){
for(j=i; j<pr; j++){
suma += niz[i][j];
}
}
printf("%d\n",suma);
//Lower triangle
pr = n;
for(i=n; i>n/2 + n%2; i--,pr--){
printf("%d",pr);
for(j=n-i; j<pr; j++){
printf("\n%d", niz[i][j]);
suma += niz[i][j];
}
}
printf("%d", suma);
}
int main()
{
int n;
printf("Matrix dimensions: ");
scanf("%d", &n);
printf("Numbers in the matrix: \n");
int niz[n][n];
write(niz, n);
x(niz, n);
}
Instead of writing separate functions for each lower, upper & diagonals you can do all together with little tricks, but it works only if row == column and thats's what you want I think.
int main() {
/* it can be anything like a[3][3] or a[7][7] and elements can
be all one or all 2 or any number */
int arr[5][5] = { {1,1,1,1,1},
{0,0,1,0,0},
{0,0,1,0,0},
{0,0,1,0,0},
{1,1,1,1,1} };
int row = sizeof(arr)/sizeof(arr[0]);
int col = sizeof(arr[0])/sizeof(arr[0][0]);
int sum = 0;
for(int index = 0; index < row; index++) {
for(int sub_index = 0; sub_index < col; sub_index++) {
if(index == 0 || (index == row-1) || sub_index == row/2)
sum = sum + arr[index][sub_index];
}
}
printf("sum = %d \n",sum);
return 0;
}
Its fine if it helps you otherwise write your own logic.
There are some mismatches between the declarations and types of the arguments passed to OP's function. While in main they declare a variable length array, named niz:
int n;
// ...
int niz[n][n];
The posted signature of both write and x requires an int niz(*)[20]. It should be changed to:
void write(int n, int niz[n][n]);
// this ^^^ may be a size_t, just remember to write it before the array
About the pattern you have to follow for the sum, I can't say to fully understand your requirement, but if I'm not completely wrong, it could be done this way:
#include <stdio.h>
#include <stdlib.h>
void read_matrix(int n, int niz[n][n])
{
for(int i=0; i<n; i++) {
for(int j=0; j<n; j++) {
scanf("%d", &niz[i][j]);
}
}
}
// Separate the calculation from the printing
int hourglass_sum(int n, int niz[n][n])
{
int sum = 0;
int i = 0;
//Upper triangle
for(int k = n; i < k; ++i, --k) {
for(int j = i; j < k; ++j) {
sum += niz[i][j];
}
}
//Lower triangle
for(int k = i + 1; i < n; ++i, ++k) {
for(int j = n - i - 1; j < k; ++j) {
sum += niz[i][j];
}
}
return sum;
}
int main()
{
int n;
printf("Matrix dimensions: ");
scanf("%d", &n);
int niz[n][n];
read_matrix(n, niz);
printf("\nSum: %d", hourglass_sum(n, niz));
}
I seem to get input for the first matrix, but when I ask the user to enter input for second matrix, the program crashes..why is this? cant figure it out, I even tried allocating memory, outcome is the same...
#include <stdlib.h>
#include <stdio.h>
#define MAXCOLUMNS 10
// dealing with 2D arrays, passing to function etc
void read_input(int (*a)[MAXCOLUMNS], int n_rows, int n_columns);
void print_sum (int (*a)[MAXCOLUMNS], int (*b)[MAXCOLUMNS], int (*c)[MAXCOLUMNS], int n_rows, int n_columns);
int main() {
int i;
int rows;
int columns;
int (*two_d_array)[MAXCOLUMNS];
int (*two_d_array2)[MAXCOLUMNS];
int (*output)[MAXCOLUMNS];
printf("enter the number of rows\n");
scanf("%d", &rows);
printf("enter the number of columns\n");
scanf("%d", &columns);
printf("enter data into array number 1\n");
read_input(two_d_array, rows, columns);
printf("enter data for 2d array number 2\n");
read_input(two_d_array2, rows, columns);
print_sum(two_d_array, two_d_array2, output, rows, columns);
return 0;
}
void read_input(int (*a)[MAXCOLUMNS], int n_rows, int n_columns) {
int i;
int j;
for (i = 0; i < n_rows; ++i) {
for (j = 0; j < n_columns; ++j) {
printf("enter details for rows number %d and column number %d\n", i + 1, j + 1);
scanf("%d", (*(a+i)+j));
getchar();
}
}
}
void print_sum (int (*a)[MAXCOLUMNS], int (*b)[MAXCOLUMNS], int (*c)[MAXCOLUMNS], int n_rows, int n_columns) {
int i;
int j;
// computing sum
for (i = 0; i < n_rows; i++) {
for (j = 0; j < n_columns; j++) {
*(*(c+i)+j) = *(*(a+i)+j) + *(*(b+i)+j);
}
}
// printing sum
for (i = 0; i < n_rows; i++) {
printf("\n");
for (j = 0; j < n_columns; j++) {
printf("%d\t", *(*(c+i)+j));
}
}
}
for C99
#include <stdlib.h>
#include <stdio.h>
#define MAXCOLUMNS 10
void read_input(int rows, int cols, int a[rows][cols]);
void print_sum (int rows, int cols, int in1[rows][cols], int in2[rows][cols], int out[rows][cols]);
int main(void) {
int i, rows, columns;
printf("enter the number of rows\n");
scanf("%d", &rows);
printf("enter the number of columns\n");
scanf("%d", &columns);
//if(columns > MAXCOLUMNS){ fprintf(stderr, "too large!"); return 1); }
int array1[rows][columns];
int array2[rows][columns];
int array3[rows][columns];
printf("enter data into array number 1\n");
read_input(rows, columns, array1);
printf("enter data for 2d array number 2\n");
read_input(rows, columns, array2);
print_sum(rows, columns, array1, array2, array3);
return 0;
}
void read_input(int rows, int cols, int a[rows][cols]){
int i, j;
for (i = 0; i < rows; ++i) {
for (j = 0; j < cols; ++j) {
printf("enter details for rows number %d and column number %d\n", i + 1, j + 1);
scanf("%d", &a[i][j]);
}
}
}
void print_sum (int rows, int cols, int a[rows][cols], int b[rows][cols], int c[rows][cols]){
int i, j;
for (i = 0; i < rows; i++){
printf("\n");,,
for (j = 0; j < cols; j++){
c[i][j] = a[i][j] + b[i][j];
printf("%d\t", c[i][j]);
}
}
}
for int ** (2D_ARRAY)
#include <stdio.h>
#include <stdlib.h>
int main(void){
int rows = 3;
int cols = 5;
int **array;
int r, c;
//allocate
array = malloc(rows * sizeof(int*));
for(r = 0; r < rows ; ++r){
array[r] = malloc(cols * sizeof(int));
}
//set
for(r = 0; r < rows ; ++r){
for(c = 0; c < cols ; ++c){
array[r][c] = r * 10 + c;
}
}
//print
for(r = 0; r < rows ; ++r){
for(c = 0; c < cols ; ++c){
printf("%02d ", array[r][c]);
}
printf("\n");
}
}
for int (**)[SIZE]
#include <stdio.h>
#include <stdlib.h>
#define MAX 10
int main(void){
int rows = 3;
int cols = 5;
int (**array)[MAX];
int r, c;
//allocate
array = malloc(rows * sizeof(int (*)[MAX]));
for(r = 0; r < rows ; ++r){
array[r] = malloc(sizeof(int[MAX]));
}
//set
for(r = 0; r < rows ; ++r){
for(c = 0; c < cols ; ++c){
(*array[r])[c] = r * 10 + c;
}
}
//print
for(r = 0; r < rows ; ++r){
for(c = 0; c < cols ; ++c){
printf("%02d ", (*array[r])[c]);
}
printf("\n");
}
}
for int (*)[SIZE]
#include <stdio.h>
#include <stdlib.h>
#define MAX 10
int main(void){
int rows = 3;
int cols = 5;
int (*array)[MAX];
int r, c;
//allocate
array = malloc(rows * sizeof(int[MAX]));
//set
for(r = 0; r < rows ; ++r){
for(c = 0; c < cols ; ++c){
array[r][c] = r * 10 + c;
}
}
//print
for(r = 0; r < rows ; ++r){
for(c = 0; c < cols ; ++c){
printf("%02d ", array[r][c]);
}
printf("\n");
}
}
I have a matrix dynamically allocated and I want to create another one which is the first matrix but with another copy beside. for example,I have the matrix:
11
22
My new matrix will be:
1 1 1 1
2 2 2 2
How can I concatenate them? This is my code in C:
#include<stdio.h>
#include<conio.h>
#include<stdlib.h>
int **create_matrix(int row, int col)
{
int **matrix = malloc(sizeof (int*)*row);
int i;
for (i = 0; i < row; i++)
{
matrix[i] = malloc(sizeof (int)*col);
}
return matrix;
}
void matrix_input(int **matrix, int row, int col)
{
int i, j;
printf("enter the elements of the matrix:\n");
for (i = 0; i < row; i++)
{
for (j = 0; j < col; j++)
{
scanf("%d", &matrix[i][j]);
}
}
}
int **extend_matrix(int **matrix, int row, int col)
{
int k, j;
int i;
int **extend_matrix = malloc(sizeof (int*)*row);
for (k = 0; k < row + row; k++)
{
extend_matrix[k] = malloc(sizeof (int)*col);
}
extend_matrix = matrix;
extend_matrix = (int**) realloc(extend_matrix, (row + row) * sizeof (int*));
extend_matrix[j] = matrix[j];
for (i = 0; i < row; i++)
{
extend_matrix[k] = matrix[i];
}
}
void print_matrix(int **matrix, int row, int col)
{
int i, j;
for (i = 0; i < row; i++)
{
for (j = 0; j < col; j++)
{
printf(" %d ", matrix[i][j]);
}
printf("\n");
}
}
void print_extend_matrix(int **extend_matrix, int row, int col)
{
int k, j;
for (k = 0; k < row + row; k++)
{
for (j = 0; j < col; j++)
{
printf("%d", extend_matrix[k][j]);
}
printf("\n");
}
}
int main(void)
{
int **matrix;
int **extend_matrix;
int row, col;
printf("enter the number of rows of cols:");
scanf("%i%i", &row, &col);
matrix = create_matrix(row, col);
matrix_input(matrix, row, col);
print_matrix(matrix, row, col);
print_extend_matrix(extend_matrix, row, col);
getch();
return 0;
}
Although #NPE suggested to you a better way. If you want to allocate memory in extend_matrix()
error in your code (read comments)
int **extend_matrix = malloc(sizeof (int*)*row);
^ on row
for (k = 0; k < row + row; k++)
^ where as loop is for row + row
{
extend_matrix[k] = malloc(sizeof (int)*col); // So this cause an error,
// segment-fault
}
second, your concept is wrong to copy memory:
extend_matrix = matrix;
at this line you are assigning matrix to extend_matrix its wrong. you need loop here to copy each elements from matrix[][] to extend_matrix[][]. (but rectify your memory allocation code first)
I think extend_matrix() should just call create_matrix() to create a new matrix of double the width, and then use two simple nested loops to populate it.
If this is what you are looking for :
int concat(void * oldM, int row, int col,void& *newM) {
newM = malloc(sizeof(int)*row*col*2);
for(int i = 0;i<2;++i)
for(int j=0;j<2;++j)
newM[i][j+col] = newM[i][j] = oldM[i][j];
for(int i = 0;i<2;++i) {
for(int j=0;j<4;++j) {
cout<<"\t"<<newM[i][j];
}
cout<<"\n";
}
}