I'm not able to read my matrix dynamically - c

My program crashes when it comes to the reading function, at the scanf line. What can I do?
I'm guessing it's an issue with the way I wrote (*(a + i) + j) but I can't tell.
void read(int **a, int n)
{
int i, j;
for(i=0;i<n;i++)
for (j = 0; j < n; j++)
{
printf("a[%d][%d]=", i, j);
scanf("%d", (*(a + i) + j)); //Access violation writing location
}
}
void show(int**a, int n)
{
int i, j;
for (i = 0; i < n; i++)
for (j = 0; j < n; j++)
{
printf("%d", *(*(a + i) + j));
}
}
int main()
{
int n,opt,a;
printf("number of lines and columns:");
scanf("%d", &n);
a = (int**)malloc(n*n * sizeof(int));
while (1)
{...

A dynamic 2D n x n array is allocated using this code:
int (*a)[n] = malloc(n * sizeof *a);
It means: Declare a as pointer to an integer array with n element and allocate n of those arrays (i.e. n * sizeof *a). In that way it ends up with n x n integers.
So a full version of your code could be like:
#include <stdio.h>
#include <stdlib.h>
void read(int n, int a[][n])
{
int i, j;
for(i=0;i<n;i++)
for (j = 0; j < n; j++)
{
printf("a[%d][%d]=\n", i, j);
scanf("%d", &a[i][j]);
}
}
void show(int n, int a[][n])
{
int i, j;
for (i = 0; i < n; i++)
{
for (j = 0; j < n; j++)
{
printf("%d ", a[i][j]);
}
puts("");
}
}
int main(void)
{
int n = 0;
printf("number of lines and columns:\n");
scanf("%d", &n);
if (n < 1) exit(1);
int (*a)[n] = malloc(n * sizeof *a);
read(n, a);
show(n, a);
free(a);
return 0;
}
note : To keep it simple I skipped all check of scanf return values. In real code, the scanf return value shall always be checked.

There is nothing wrong with allocating a block using malloc ( n * n * sizeof *a);
The address of the block must be assigned to a pointer int *a
Elements can be accessed by (a + i * n + j) or a[i * n +j]
void read(int *a, int n)
{
int i, j;
for(i=0;i<n;i++)
for (j = 0; j < n; j++)
{
printf("a[%d][%d]=", i, j);
scanf("%d", (a + i * n + j));
// scanf("%d", &a[i * n + j]);
}
}
void show(int *a, int n)
{
int i, j;
for (i = 0; i < n; i++)
for (j = 0; j < n; j++)
{
printf("%d", *(a + i * n + j));
// printf("%d", a[i * n + j]);
}
}
int main()
{
int n = 0, opt = 0, *a = NULL;
printf("number of lines and columns:");
scanf("%d", &n);
a = malloc ( n * n * sizeof *a);
while (1)
{...

Related

initialization of arrays while operating with mallocs

Given the following piece of code, I don't understand why do we have to initialize every single row of the matrix when we have already created enough space in the stack.
#include <stdio.h>
#include <stdlib.h>
main() {
int **w;
int i, j;
int m, n;
printf("Number of rows in the matrix: ");
scanf("%d", &m);
printf("Number of columns in the matrix: ");
scanf("%d", &n);
w = (int **)malloc(m * n * sizeof(int));
for (i = 0; i < m; i++)
w[i] = (int *)malloc(n * sizeof(int));
for (i = 0; i < m; i++)
for (j = 0; j < n; j++) {
printf("Element [%d][%d]: ", i + 1, j + 1);
scanf("%d", &w[i][j]);
}
for (i = 0; i < m; i++)
for (j = 0; j < n; j++)
printf("Element [%d][%d]: %d\n", i + 1, j + 1, w[i][j]);
}
There are many issues in your code:
space is not allocated on the stack, but from the heap.
in both cases, memory allocated for the objects is uninitialized, which means it is not initialized to anything in particular and can have any value whatsoever. Relying on any particular contents is undefined behavior.
the matrix dimensions and all the matrix elements are read from standard input with scanf(). Yet you do not check for scanf() failure to convert integers from the characters read from stdin, so any invalid or missing input is going to cause undefined behavior at some point in the program.
your matrix is actually structured as an array of pointers to arrays of int, which is fine, but inconsistent with the size arguments used to allocate the first array: w = (int **)malloc(m * n * sizeof(int)); should be
w = malloc(m * sizeof(*w));
you could easily get objects pre-initialized to 0 by using calloc() instead of malloc():
for (i = 0; i < m; i++)
w[i] = calloc(n, sizeof(int));
you should also check for malloc() failure and exit with an appropriate diagnostic message.
main() is an obsolete prototype for the main function. You should either use int main(), int main(void) or int main(int argc, char *argv[])...
Here is a modified version:
#include <stdio.h>
#include <stdlib.h>
int get_int(void) {
int n;
if (scanf("%d", &n) != 1) {
printf("invalid input\n");
exit(EXIT_FAILURE);
}
return n;
}
void xalloc(size_t size) {
void *p = calloc(size, 1);
if (p == NULL) {
printf("out of memory for %zu bytes\n", size);
exit(EXIT_FAILURE);
}
return p;
}
int main() {
int **w;
int i, j;
int m, n;
printf("Number of rows in the matrix: ");
m = get_int();
printf("Number of columns in the matrix: ");
n = get_int();
w = xalloc(m * sizeof(*w));
for (i = 0; i < m; i++) {
w[i] = xalloc(n * sizeof(int));
}
for (i = 0; i < m; i++) {
for (j = 0; j < n; j++) {
printf("Element [%d][%d]: ", i + 1, j + 1);
w[i][j] = get_int();
}
}
for (i = 0; i < m; i++) {
for (j = 0; j < n; j++) {
printf("Element [%d][%d]: %d\n", i + 1, j + 1, w[i][j]);
}
}
for (i = 0; i < m; i++) {
free(w[i]);
}
free(w);
return 0;
}

Difference between malloc and calloc in this case?

This is a code for multiplying two square matrices in C.
What is the difference between using malloc and calloc in void multiply() function?
When using malloc, I am getting garbage values, but calloc is providing the right answer.
Only the first row is outputting garbage values so is it an issue with the way malloc allocates space in the heap as compared to calloc?
#include <stdio.h>
#include <stdlib.h>
int *getArray(int);
void display(int *, int, int);
void multiply(int *, int *, int);
int main() {
int n;
printf("enter dimension of square matrix:\n");
scanf("%d", &n);
int *arr1;
int *arr2;
arr1 = getArray(n);
display(arr1, n, n);
printf("\n now give input for next array");
arr2 = getArray(n);
display(arr2, n, n);
printf("\n\n\n");
multiply(arr1, arr2, n);
return 0;
}
int *getArray(int n) {
int *arr = (int *)malloc(n * n * sizeof(int));
printf("\n");
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
scanf("%d", (arr + i * n + j));
}
}
/*for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
printf(" %d ", *(arr + i * n + j));
}
printf("\n");
}*/
return arr;
}
void display(int *arr, int row, int col) {
for (int i = 0; i < row; i++) {
for (int j = 0; j < col; j++) {
printf(" %d ", *(arr + i * row + j));
}
printf("\n");
}
}
void multiply(int *arr1, int *arr2, int n) {
int *arr = (int *)calloc(n * n, sizeof(int));
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
for (int k = 0; k < n; k++) {
*(arr + i * n + j) += (*(arr1 + i * n + k)) * (*(arr2 + k * n + j));
}
}
}
printf("product of above matrices = \n\n");
display(arr, n, n);
}
The only functional difference between allocating memory with malloc() and with calloc() for the same size, assuming the size computation is accurate, is the latter initializes the block to all bits 0, whereas the former does not.
All bits 0 means all int values in the array are initialized to 0.
The inner loop in the multiply function only increments the element at row i and column j, therefore the function relies on implicit initialization of the array elements to 0. calloc() does that, but not malloc() so you definitely need to use calloc().
Also note these remarks:
in display the computation for the offset of the matrix element at row i column j should be printf(" %5d ", *(arr + i * col + j));
multiply should return arr and display() should be called in the main function.
you should check for scanf(), malloc() and calloc()` failure
you should free allocated memory
pointer arguments to objects that are not modified by the function should be const qualified so the function can be called with a pointer to a const object.
Here is a modified version:
#include <stdio.h>
#include <stdlib.h>
int *getArray(int);
void display(const int *, int, int);
int *multiply(const int *, const int *, int);
int main() {
int n;
printf("enter dimension of square matrix:\n");
if (scanf("%d", &n) != 1)
return 1;
printf("\n now give input for the first array");
int *arr1 = getArray(n);
if (!arr1)
return 1;
display(arr1, n, n);
printf("\n now give input for the second array");
int *arr2 = getArray(n);
if (!arr2)
return 1;
display(arr2, n, n);
printf("\n\n\n");
int *arr = multiply(arr1, arr2, n);
if (!arr)
return 1;
printf("product of above matrices = \n\n");
display(arr, n, n);
free(arr1);
free(arr2);
free(arr);
return 0;
}
int *getArray(int n) {
int *arr = malloc(sizeof(int) * n * n);
if (arr == NULL)
return NULL;
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
if (scanf("%d", (arr + i * n + j)) != 1) {
free(arr);
return NULL;
}
}
}
return arr;
}
void display(const int *arr, int row, int col) {
for (int i = 0; i < row; i++) {
for (int j = 0; j < col; j++) {
printf(" %5d ", *(arr + i * col + j));
}
printf("\n");
}
}
int *multiply(const int *arr1, const int *arr2, int n) {
int *arr = calloc((size_t)n * n, sizeof(int));
if (arr == NULL)
return NULL;
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
for (int k = 0; k < n; k++) {
*(arr + i * n + j) += (*(arr1 + i * n + k)) * (*(arr2 + k * n + j));
}
}
}
return arr;
}

Error in a C program using dynamic memory allocation and array

Programming in C for finding maximum in 2D array using dynamic memory allocation.
int main() {
int i, arr[m][n], j, m, n;
int max = 0;
int *ptr;
printf("enter the value m");
scanf("%d", m);
printf("enter the vaue of n");
scanf("%d", n);
ptr = (int*) malloc(m * n * 4);
printf("enter the values\n");
for (i = 0; i < m; i++)
{
for (j = 0; j < n; j++)
{
scanf("%d", ((ptr + i * n) + j));
}
}
max = arr[0][0];
for (i = 0; i < m; i++)
{
for (j = 0; j < n; j++)
{
if (max < *((ptr + i * n) + j));
max = *((ptr + i * n) + j);
}
}
printf("%d", max);
}
I made changes to your code to remove the error you are getting. I commented the changes that I have made.
int main()
{
/*int i, arr[][], j, m, n;*/
/* Because arr is allocated dynamically, you have to declare as a pointer to int. */
int i, *arr, j, m, n;
int max = 0;
int *ptr;
printf("enter the value m");
scanf("%d", m);
printf("enter the vaue of n");
scanf("%d", n);
/*ptr = (int*)malloc(m * n * 4);*/
/* It is better to use sizeof(int) because int does not have the same length of all computers. */
ptr = (int*)malloc(m * n * sizeof(int));
printf("enter the values\n");
for (i = 0; i < m; i++)
{
for (j = 0; j < n; j++)
{
scanf("%d", ((ptr + i * n) + j));
}
}
/*max = arr[0];*/
/* To get the first int at arr, you could also use arr[0], but not arr[0][0] because */
/* this would require that arr be an array of pointers to array of int's, which is not the case. */
max = *arr;
for (i = 0; i < m; i++)
{
for (j = 0; j < n; j++)
{
if (max < *((ptr + i * n) + j));
max = *((ptr + i * n) + j);
}
}
printf("%d", max);
}
You must learn the algorithms and programming language C.
So you can find some courses in this site :
learn-c
try this code is functioned:
#include <stdio.h>
#include <stdlib.h>
int main(int argc, char const *argv[]) {
int i, j, m, n;
int max;
int **ptr;
printf("enter the value m: ");
scanf("%d", &m);
printf("enter the vaue of n: ");
scanf("%d", &n);
ptr = (int **)malloc(n * sizeof(int *));
for (i = 0; i < m; i++) {
*(ptr + i) = (int *)malloc(m * sizeof(int));
for (j = 0; j < n; j++) {
scanf("%d", (*(ptr + i) + j));
}
}
max = **ptr;
printf("\n\nMatrix:\n");
for (i = 0; i < m; i++) {
for (j = 0; j < n; j++) {
printf("%d ", *(*(ptr + i) + j));
if (max < *(*(ptr + i) + j))
max = *(*(ptr + i) + j);
}
printf("\n");
}
printf("\nthe max is %d \n", max);
return 0;
}

C: Why doesn't this code work?

Need help with this code it should return c[] with the number's of a[] % b[] = 0 but it doesn't work.
#define _CRT_SECURE_NO_WARNINGS
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int *divide(int a[], int a_size, int b[], int b_size)
{
int i = 0, j = 0, k = 0, counter = 0, *c;
c = (int*)malloc(b_size * sizeof(int));
for (i = 0; i < b_size; i++)
{
for (j = 0; j < a_size; j++)
{
if (a[j] % b[i] == 0)
counter++;
}
c[k] = counter;
k++;
counter = 0;
}
for (int t = 0; t < b_size; t++)
{
printf("%d ", c[t]);
}
printf("\n");
}
main ()
{
int *a, *b, a_size, b_size;
printf("Enter size of a:\n");
scanf ("%d", &a_size);
a = (int*)malloc(a_size * sizeof(int));
printf("\nEnter size of b:\n");
scanf("%d", &b_size);
b = (int*)malloc(b_size * sizeof(int));
printf("\nEnter elements of a:\n");
for (int i = 0; i < a_size; i++)
{
scanf("%d", &a[i]);
}
printf("\nEnter elements of b:\n");
for (int j = 0; j < b_size; j++)
{
scanf("%d", &b[j]);
}
divide(&a, a_size, &b, b_size);
}
There was some errors in your code.
You want your fonction *divide(...) to return a new array containing the operation a[i] % b[i], but your function doesn't return anything, so you have to return it. It seems more logical to print the new array in the main, than in the function while doing it.
When you pass the variables to your function be careful to pass int*, not int **.
Here is a sample of code which works (you didn't say what to do if a_size and b_size were different so I assume we only use the smallest size and don't treat the number after) :
#define _CRT_SECURE_NO_WARNINGS
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int *divide(int a[], int a_size, int b[], int b_size)
{
int i = 0, stop, *c;
if (b_size <= a_size)
{
c = (int*)malloc(b_size * sizeof(int));
stop = b_size;
}
else
{
c = (int*)malloc(a_size * sizeof(int));
stop = a_size;
}
while (i < stop)
{
c[i] = a[i] % b[i];
i++;
}
return (c);
}
int main ()
{
int *a, *b, a_size, b_size;
int *result = NULL;
int stop;
int i = 0;
printf("Enter size of a:\n");
scanf ("%d", &a_size);
a = (int*)malloc(a_size * sizeof(int));
printf("\nEnter size of b:\n");
scanf("%d", &b_size);
b = (int*)malloc(b_size * sizeof(int));
printf("\nEnter elements of a:\n");
for (int i = 0; i < a_size; i++)
{
scanf("%d", &a[i]);
}
printf("\nEnter elements of b:\n");
for (int j = 0; j < b_size; j++)
{
scanf("%d", &b[j]);
}
result = divide(a, a_size, b, b_size); //not &a neither &b because it would be a char** instead of a char*
if (a_size < b_size)
stop = a_size;
else
stop = b_size;
while (i < stop)
{
printf("%d ", result[i]);
i++;
}
return 0;
}

While Performing 2D array representation in memory leads to Segmentation fault: 11

I've presented the codes below only while executing the first loop it works fine but as soon as i uncomment the second loop it starts to throw segmentation fault. My code is as below.
// Write a program to add two m*n matrices using pointer.
#include <stdio.h>
#define m 2
#define n 2
int main() {
int (*a)[n];
int (*b)[n], i, j; //, *(sum)[n], i, j;
printf("Enter first matrix:\n");
for (i = 0; i < m; i++) {
for (j = 0; j < n; j++) {
scanf("%d", *(a + i) + j);
}
}
printf("Enter second matrix:\n");
for (i = 0; i < m; i++) {
for (j = 0; j < n; j++) {
scanf("%d", *(b + i) + j);
}
}
// printf("The Sum of matrix is:\n");
// for (i = 0; i < m; i++) {
// for (j = 0; j < n; j++) {
// // *(*(sum + i) + j) = *(*(a + i) + j) + *(*(b + i) + j);
// // printf("\t%d", *(*(sum + i) + j));
// }
// printf("\n");
// }
}
You are not defining a and b as 2D arrays, but as uninitialized pointers to 2D arrays. passing addresses into these invokes undefined behavior. You must make these pointers point to an actual array, either static, automatic or allocated from the heap.
You can define 2D arrays this way:
int a[m][n], b[m][n];
If you are required to use pointers, you can allocate the 2D arrays with malloc:
int (*a)[n] = malloc(sizeof(*a) * m);
int (*b)[n] = malloc(sizeof(*b) * m);
In your program, it is more readable to use the [] syntax, even for pointers:
#include <stdio.h>
#include <stdlib.h>
#define m 2
#define n 2
int main(void) {
int (*a)[n] = malloc(sizeof(*a) * m);
int (*b)[n] = malloc(sizeof(*b) * m);
int (*sum)[n] = malloc(sizeof(*sum) * m);
printf("Enter first matrix:\n");
for (int i = 0; i < m; i++) {
for (int j = 0; j < n; j++) {
scanf("%d", &a[i][j]);
}
}
printf("Enter second matrix:\n");
for (int i = 0; i < m; i++) {
for (int j = 0; j < n; j++) {
scanf("%d", &b[i][j]);
}
}
printf("The Sum of matrices is:\n");
for (int i = 0; i < m; i++) {
for (int j = 0; j < n; j++) {
sum[i][j] = a[i][j] + b[i][j];
printf("\t%d", sum[i][j]);
}
printf("\n");
}
return 0;
}

Resources