Reputation: 29
This is a simple program to find the smallest element of an array. But the previous versions of the following program gave an error where the smallest and largest numbers were displayed as 0. In the following version of the program, the compiler is giving me a segmentation error.
#include <stdio.h>
void minimum();
void maximum();
int n;
int main()
{
int array[n];
printf("Enter the size of your array:\n");
scanf("%d", &n);
printf("Enter the elements of your array:\n");
for (int i = 0; i < n; i++)
{
printf("Enter element %d:\n", i + 1);
scanf("%d", array);
}
minimum(array[n]);
maximum(array[n]);
return 0;
}
void minimum(int arr[n])
{
int* min;
min = &arr[0]; // Initialize min to the value of the first element of the array
for (int i = 1; i < n; i++)
{
if (*(arr+i)<*min)
{
*min = *(arr+i);
}
}
printf("The smallest element in the array is: %d\n", *min);
}
void maximum(int arr[n])
{
int* max;
max = &arr[0]; // Initialize min to the value of the first element of the array
for (int i = 1; i < n; i++)
{
if (*(arr+i)>*max)
{
*max = *(arr+i);
}
}
printf("The greatest element in the array is: %d\n", *max);
}
In the previous versions of this program I tried to pass two parameters to the function declaration first with only one int* and second with one int* and an int, both of which resulted in the smallest and biggest number being 0 although it should have been some other numbers. I also tried to pas the min and max to the functions along with the array pointer like void min(int*, int*);
which also gave an output where nim and max both equal to 0.
#include <stdio.h>
void minimum(int *, int);
void maximum(int *, int);
int main()
{
int n;
int array[100];
printf("Enter the size of your array:\n");
scanf("%d", &n);
printf("Enter the elements of your array:\n");
for (int i = 0; i < n; i++)
{
printf("Enter element %d:\n", i + 1);
scanf("%d", array);
}
minimum(array, n);
maximum(array, n);
return 0;
}
void minimum(int *arr, int n)
{
int *min = &arr[0]; // Initialize min to the value of the first element of the array
for (int i = 1; i < n; i++)
{
if (*(arr+i)<*min)
{
*min = *(arr+i);
}
}
printf("The smallest element in the array is: %d\n", *min);
}
void maximum(int *arr, int n)
{
int *max = &arr[0]; // Initialize min to the value of the first element of the array
for (int i = 1; i < n; i++)
{
if (*(arr+i)>*max)
{
*max = *(arr+i);
}
}
printf("The greatest element in the array is: %d\n", *max);
}
Upvotes: 1
Views: 108
Reputation: 4588
int array[n];
n
has size 0
as it has static storage duration
minimum(array[n]);
You do not pass the array only a single element of the array and it invokes undefined behaviours.
array
outside its bounds as indexes are from 0
to n - 1
.In C language you always need to pass the size of the array. Arrays are passed by pointers.
This makes no sense as you will modify the array if you find a number larger or smaller.
int* min;
min = &arr[0];
Your function prototypes do not match actual definitions.
This program have more issues than lines. I would suggest to read again pointer and arrays chapter in your favourite C book
int main(void)
{
size_t size;
printf("Enter the size of your array:\n");
if(scanf("%zu", &size) != 1) { /* handle error */ }
int array[size];
printf("Enter the elements of your array:\n");
for (size_t i = 0; i < size; i++)
{
printf("Enter element %d:\n", i + 1);
if(scanf("%d", array + i) != 1) { /* handle error */ }
}
printf("The smallest element in the array is: %d\n", minimum(array, size));
printf("The smallest element in the array is: %d\n", maximum(array, size));
}
int minimum(const int *arr, size_t size)
{
int min = 0;
if(arr && size)
{
min = arr[0];
for (size_t i = 1; i < size; i++)
{
if (arr[i] < min)
{
min = arr[i];
}
}
}
return min;
}
int maximum(const int *arr, size_t size)
{
int min = 0;
if(arr && size)
{
min = arr[0];
for (size_t i = 1; i < size; i++)
{
if (arr[i] > min)
{
min = arr[i];
}
}
}
return min;
}
Upvotes: 0
Reputation: 155363
You have many problems here:
You've invoking undefined behavior when you declare int array[n];
before n
is given a non-zero value, then try to access any elements of said array (technically, I believe C forbids even declaring zero-length arrays, but it's commonly supported to support inlined variable length terminal arrays on a struct). At the point you declared array
, n
was zero, so no space is allocated to hold anything. Even with C's variable length array support, n
needs to hold the correct value first.
scanf("%d", array);
is repeatedly reading into the first index of array
, not sequential indices. You wanted scanf("%d", &array[i]);
.
minimum(array[n]);
and maximum(array[n]);
are nonsensical; you're passing the value one past the end of the array, as if it were a pointer (turn on your compiler warnings, this was an obvious one it should have caught). You wanted minimum(array);
and maximum(array);
With all that fixed, your working main
is:
int main()
{
printf("Enter the size of your array:\n");
scanf("%d", &n);
int array[n]; // Declared *after* n has a value
printf("Enter the elements of your array:\n");
for (int i = 0; i < n; i++)
{
printf("Enter element %d:\n", i + 1);
scanf("%d", &array[i]); // Initializing sequential elements
}
minimum(array); // Passing pointer to array's first element, not value of past-the end element
maximum(array); // Ditto
return 0;
}
You minimum
and maximum
functions also have issues, confusing values and pointers.
int* min;
min = &arr[0];
(a long-winded way to spell int *min = arr;
) is initially making min
a pointer. But *min = *(arr+i);
is assigning the value where it points, not changing where it points (so the array gets mutated in the process of finding the minimum value). The code works, it's just since the caller should not expected a logical read-only operation to change their array.
You can do this two ways, either with pointers (to preserve knowledge of where the minimum was found) or with values (ignoring positional info). With pointers, it looks like:
void minimum(const int arr[n]) // Mark const to ensure compiler warns you if you modify it
{
int *min = arr; // Initialize min to pointer to first element of array
for (int i = 1; i < n; i++)
{
if (arr[i]<*min) // Compare values, requires dereference because min is a pointer
{
min = &arr[i]; // Update to point to newly found minimum value by taking address where value found
}
}
printf("The smallest element in the array is: %d\n", *min); // Print value by dereferencing
}
Alternatively (and typically slightly more efficiently), you operate by value, discarding information about where the element was found:
void minimum(const int arr[n]) // Mark const to ensure compiler warns you if you modify it
{
int min = arr[0]; // Initialize min to value of first element of array, not a pointer
for (int i = 1; i < n; i++)
{
if (arr[i]<min) // Compare values, no dereference of min involved because it's a raw value
{
min = arr[i]; // Update to newly found minimum value, again, only dereferencing arr, not min
}
}
printf("The smallest element in the array is: %d\n", min); // Again, min a value, no dereferencing
}
Either works, and neither involves destructively computing minimums or maximums.
Upvotes: -1