Finding sum of the array elements using pointers using following code.
i dont know why program is not ending at the end of the array!!
#include <stdio.h>
#define LEN(a) (int) (sizeof(a)/sizeof(a[0]))
int sum_array(int * , int);
int main(void){
int a[] = {1,2,3,4,5,6,7,8,9};
printf("Array length %d\n",LEN(a));
int sum = sum_array(a,LEN(a));
printf("Sum of array is %d\n",sum);
return 0;
}
int sum_array( int * p , int n){
int sum = 0;
while ( p < p+n ){
printf("Sum of array is %d\n",sum);
sum += *p++;
}
return sum;
}
`
SOLVED GUYS thanks!!
int sum_array( int * a , int n){
int sum = 0, *p=a;
while ( p < a+n ){
printf("Sum of array is %d\n",sum);
sum += *p++;
}
return sum;
getting address boundary error!!
How can p < p + n ever be 1 for a non-negative n?
You need to store the initial value of p somewhere if you want to bound the loop that way.
For an easy life use for (int i = 0; i < n; ++i) in place of while (p < p + n) and adopt, if you must and against any professional advice, a flashy version once you have the basics correct.
The problem is that within the condition of the loop you are using the pointer that is changed within the loop.
while ( p < p+n ){
printf("Sum of array is %d\n",sum);
sum += *p++;
}
So the condition never will be equal to false except when n is equal to 0.
The function can be declared and defined the following way
long long int sum_array( const int *p , size_t n );
Pay attention to that within the function the array is not changed. So the first parameter should have the qualifier const.
And
long long int sum_array( const int *p , size_t n )
{
long long int sum = 0;
for ( const int *q = p; q < p + n; ++q )
{
sum += *q;
}
return sum;
}
If you want to use the while loop then the pointer q need to be defined outside the loop
const int *q = p;
while ( q < p + n )
{
sum += *q++;
}
Also do the following changes
#define LEN(a) (sizeof(a)/sizeof(a[0]))
and
printf("Array length %zu\n",LEN(a));
long long int sum = sum_array(a,LEN(a));
printf( "Sum of array is %lld\n",sum);
The type long long int is used for the variable sum because in general there can be an overflow.
Consider for example the following demonstrative program
#include <stdio.h>
#include <limits.h>
#define LEN(a) (sizeof(a)/sizeof(a[0]))
int sum_array( const int * , size_t );
int main(void)
{
int a[] = { INT_MAX, 1 };
printf("Array length %zu\n",LEN(a));
int sum = sum_array( a, LEN( a ) );
printf("Sum of array is %d\n",sum);
return 0;
}
int sum_array( const int *p , size_t n )
{
int sum = 0;
const int *q = p;
while ( q < p + n )
{
sum += *q++;
}
return sum;
}
Its output is
Array length 2
Sum of array is -2147483648
It is evident that the result is not what you are expecting.
If to make the type of the variable sum long long int then the result will be correct.
#include <stdio.h>
#include <limits.h>
#define LEN(a) (sizeof(a)/sizeof(a[0]))
long long int sum_array( const int * , size_t );
int main(void)
{
int a[] = { INT_MAX, 1 };
printf("Array length %zu\n",LEN(a));
long long int sum = sum_array( a, LEN( a ) );
printf("Sum of array is %lld\n",sum);
return 0;
}
long long int sum_array( const int *p , size_t n )
{
long long int sum = 0;
const int *q = p;
while ( q < p + n )
{
sum += *q++;
}
return sum;
}
The program output is
Array length 2
Sum of array is 2147483648
Related
I am studying the pointers and this question became interesting. I want it to be like this: we have two arrays of integers. Determine the value and number of the largest element of the first array that is not part of the second but I don't know how to make the second part of the code that will check if the largest number is not included in the second array
#include <stdio.h>
int main()
{
long array[100], * maximum, size, c, location = 1;
printf("Enter the number of elements in array\n");
scanf_s("%ld", &size);
printf("Enter %ld integers\n", size);
for (c = 0; c < size; c++)
scanf_s("%ld", &array[c]);
maximum = array;
*maximum = *array;
for (c = 1; c < size; c++)
{
if (*(array + c) > *maximum)
{
*maximum = *(array + c);
location = c + 1;
}
}
printf("Maximum element is present at location number %ld and it's value is %ld.\n", location, *maximum);
return 0;
}
For starters your incomplete code already is wrong. It changes the source array
maximum = array;
//...
*maximum = *(array + c);
More precisely it changes the first element of the array. It shall not do that.
As for your question then the code will look more clear and readable if to implement the algorithm as separate functions.
Here is a demonstration program.
#include <stdio.h>
int find( const int a[], size_t n, int value )
{
const int *p = a;
while (p != a + n && *p != value) ++p;
return p != a + n;
}
int * max_exclusive_element( const int a1[], size_t n1, const int a2[], size_t n2 )
{
const int *max = a1;
while (max < a1 + n1 && find( a2, n2, *max ) ) ++max;
if (max < a1 + n1)
{
for ( const int *p = max; ++p < a1 + n1; )
{
if ( *max < *p && !find( a2, n2, *p ) )
{
max = p;
}
}
}
return ( int * )( max == a1 + n1 ? NULL : max );
}
int main( void )
{
int a1[] = { 1, 3, 5, 6, 7, 8, 9 };
const size_t N1 = sizeof( a1 ) / sizeof( *a1 );
int a2[] = { 1, 3, 5, 7, 9 };
const size_t N2 = sizeof( a2 ) / sizeof( *a2 );
int *max = max_exclusive_element( a1, N1, a2, N2 );
if (max != NULL)
{
printf( "Maximum element is present at location number %td and it's value is %d.\n",
max - a1, *max );
}
}
The program output is
Maximum element is present at location number 5 and it's value is 8.
The function find determines whether a given value is present in an array. And the second function max_exclusive_element finds the maximum element according to the requirement.
As you can see all loops use pointers.
If you need to use arrays with elements of the type long int then it will be not hard to change the presented code.
I think you are doing this in the wrong order. If you find the maximum first and that is in the second array, you need to find the maximum again. You should first check each number in the first array against the second. If it is in the second, change the value to LONG_MIN. Then the maximum will be the right answer. Basically something like this:
#include <limits.h>
int i = 0;
for (; i < n; ++i) {
int j = 0;
for (; j < n; ++j) {
/* in both arrays? */
if (arr2[i] == arr1[j]) {
arr1[j] = LONG_MIN;
break;
}
}
}
At this point any numbers in arr1 that are in arr2 will be set to LONG_MIN. Now just calculate max like you already did.
Edit: changed INT_MIN to LONG_MIN. I didn't notice you were doing long int arrays.
I dont know how to get the code to print out the elements that are divisable with 3 and the print out the sum of those elements , can someone help me do it , thanks for your time!
Code:
#include <stdio.h>
int sum(int arr[]){
int n = sizeof(arr) / sizeof(arr[0]);
int sum = 0;
for (int y=0;y<n;y++){
sum += arr[y];
printf("%d",sum);
}
}
int main() {
int F[5] = {1,3,5,9,8};
int s = 0;
for (int i=0;i<5;i++){
if (F[i]%3 == 0) {
int diviz[] = {F[i]};
printf("%d\n",diviz[0]);
sum(diviz);
}
}
return 0;
}
Expected Output:
3
9
12
Actual Output:
3
349
910
Idk how to solve this issue
This function declaration
int sum(int arr[]){
is adjusted by the compiler to the declaration
int sum(int *arr){
That is within the function the variable arr has the pointer type int *.
Thus the declaration with sizeof expression
int n = sizeof(arr) / sizeof(arr[0]);
is equivalent to
int n = sizeof( int * ) / sizeof( int );
and yields either 2 or 1 depending on the size of the pointer.
On the other hand, this call of the function
int diviz[] = {F[i]};
printf("%d\n",diviz[0]);
sum(diviz);
in any case does not make a great sense because instead of passing the original array you are passing an array that contains only one element. And the for loop in main is redundant.
You need explicitly to pass the number of elements in the array.
So the function can look like
long long int sum( const int arr[], size_t n, int divisor )
{
long long int sum = 0;
for ( size_t i = 0; i < n; i++ )
{
if ( arr[i] % divisor == 0 ) sum += arr[i];
}
return sum;
}
And the function can be called like
int arr[] = {1,3,5,9,8};
const size_t N = sizeof( arr ) / sizeof( *arr );
int divisor = 3;
printf( "The sum of elements divisible by %d = %lld\n", divisor, sum( arr, N, divisor ) );
The function will be more safer if to add a check whether divisor is passed equal to 0 as for example
long long int sum( const int arr[], size_t n, int divisor )
{
long long int sum = 0;
if ( divisor != 0 )
{
for ( size_t i = 0; i < n; i++ )
{
if ( arr[i] % divisor == 0 ) sum += arr[i];
}
}
return sum;
}
int main() {
int F[5] = {1,3,5,9,8};
int s = 0;
for (int i=0;i<5;i++){
if (F[i]%3 == 0) {
s = s + F[i];
printf("%d",F[i]);
}
}
printf("%d",s); //print sum total
return 0;
}
The task is to fill an array with numbers by user input and then use our stats() function to calculate average etc. of each row of this array. The header of stats() function looks as follows:
int stats(int (*ptr)[5], int width, int height, int row_id, int* max, int* min, float *avg)
where ptr is a pointer to the matrix,width and height are its size, row_id is the index of analysed row and max, min and avg are pointers to variables storing each statistics.
When calling a function with such line:
stats(*ptr, 5,5,2, *max = NULL, *min = NULL, *avg=NULL);
the following error appears:
error: invalid type argument of unary '*' (have 'int')
I tried different approaches but there is always a mistake, how can I fix that? Thank you for any clues.
edit:
Here's the whole code:
#include <stdio.h>
int stats(int (*ptr)[5], int width, int height, int row_id, int* max, int* min, float *avg)
{
int j, vmax,vmin;
int max = &vmax;
int min = &vmin;
int i = row_id;
int m = *ptr;
for(j = 0; j<5; j++){
if(m[i][j]>max)
{
max = m[i][j] ;
j++;
else
j++;
}
}
printf("%d", max);
return 0;
}
int main(void){
int n, i, j, vmin, vmax; // vmax - value of the maximum
int min = &vmin; // min - pointer to the minimum
int max = &vmax;
float vavg;
int avg = &vavg;
int m[5][5];
for(i = 0; i<5; i++)
{
for(j = 0; j<5; j++)
{
printf("ENTER A NUMBER: ");
scanf("%d", &n);
m[i][j] = n;
}
}
int ptr = &m;
stats(*ptr, 5,5,2, *max = NULL, *min = NULL, *avg=NULL);
return 0;
}
Your code full of bugs.
For example min and max are not declared as pointers
int min = &vmin; // min - pointer to the minimum
int max = &vmax;
Also it is unclear why the variable avg has the type int and is initialized by a pointer expression of the type float *.
float vavg;
int avg = &vavg;
Or the variable ptr of the type int is initialized by the address of the two-dimensional array.
int ptr = &m;
As for the function then if the function operates only on one row then there is no any sense to pass to the function the whole two-dimensional array.
Also the return type and the returned value of the function do not make a sense.
And the function shall not output any message. It is the caller of the function that will decide output a message or not.
And also the function contains bugs where you are redeclaring its parameters like for example
int max = &vmax;
that again does not make a sense.
Using your approach the function can be declared and defined the following way
#include <assert.h>
//...
void stats( const int *a, size_t n, int *max, int *min, float *avg )
{
assert( n != 0 );
*max = a[0];
*min = a[0];
float sum = a[0];
for( size_t i = 1; i < n; i++ )
{
sum += a[i];
if ( *max < a[i] )
{
*max = a[i];
}
else if ( a[i] < *min )
{
*min = a[i];
}
}
*avg = sum / n;
}
And called like
int min = 0;
int max = 0;
float avg = 0.0f;;
//...
stats( m[2], 5, &max, &min, &avg );
printf( "max = %d\n", max );
printf( "min = %d\n", min );
printf( "average = %f\n", avg );
When you are using pointers as function parameters be carefull. If you have something like this:
int func(int *max){
}
max ,here, is a pointer which needs to hold an address. So inside this function when you need use it, you need to dereference it by using *. For example:
int func(int *max){
*max = $someAddress
}
Can someone help me fixing the syntax errors in this code?
#include <stdio.h>
int result(int v, int size);
int main(void){
int arr[5], n;
for (n = -1; n < 4; n++){
arr[n] = n + 1;
printf("the product of entered values is %d", result(n, 5));
}
return 0;
}
int product(int a[]) {
int product, i;
for (i = 0; i <= sizeof(int); i++){
product *= a[i];
}
return product;
}
for (n = -1; n < 4; n++){
arr[n] = n + 1;
You start n at -1, then immediately use arr[n].
Negative indices are not allowed in C. Valid values are 0 to the size of the array-1.In otherwords, if you have an arr[5], then the valid indices are [0], [1], [2], [3], and [4].
int product(int a[]) {
int product, i;
You create a function named product and also a variable named product.
That makes it virtually impossible to refer to the proper object. Work on your name management, so that every item is unambiguous.
You are trying to call the result function, for which you have provided the forward declaration but not an actual implementation. You need to write an implementation for the result function. That is why the compiler complains about an undefined reference.
For starters the function result is declared
int result(int v, int size);
but not defined.
On the other hand, taking into account the message in this call of printf
printf("the product of entered values is %d", result(n, 5));
you mean a function that calculates a product of elements of an array like your function defined after main but that is not used
int product(int a[]) {
int product, i;
for (i = 0; i <= sizeof(int); i++){
product *= a[i];
}
return product;
}
So let's remove the declaration of the function result and declare before main a function with name product because the name result is not enough informative.
The function deals with an array. We need to pass to the function the number of elements in the array. As the array itself will not be changed within the function then it should be declared with the qualifier const
Also a product of integer numbers of the type int can be too big to be stored in an object of the type int.
So it is better to declare the return type of the function at least like long long int (or even like double or long double).
Thus the function declaration can look like
long long int product( const int a[], size_t n );
The function can be defined the following way
long long int product( const int a[], size_t n )
{
long long int result = n == 0 ? 0 : 1;
for ( size_t i = 0; i < n; i++ )
{
result *= a[i];
}
return result;
}
As for your function product then you forgot to initialize the variable product
int product, i;
The condition in the for loop
for (i = 0; i <= sizeof(int); i++){
does not make a sense because the expression sizeof( int ) does not yield the number of elements in an array.
Try to not use magic numbers like 5 in this declaration
int arr[5], n;
in your programs. Use named constants.
Indices of arrays always start from 0. So this loop
for (n = -1; n < 4; n++){
where the variable n is used as an index does not make sense.
Also this call of printf
printf("the product of entered values is %d", result(n, 5));
must be placed outside the for loop and in the the call of the function result that is used as an argument of the function printf
result(n, 5)
you even are not using the array.
Thus the program can look the following way
#include <stdio.h>
long long int product( const int a[], size_t n );
int main(void)
{
enum { N = 5 };
int a[N];
for ( size_t i = 0; i < N; i++ )
{
a[i] = i + 1;
}
printf( "The product of entered values is %lld", product( a, N ) );
return 0;
}
long long int product( const int a[], size_t n )
{
long long int result = n == 0 ? 0 : 1;
for ( size_t i = 0; i < n; i++ )
{
result *= a[i];
}
return result;
}
The program output is
The product of entered values is 120
I have to use the recursive selection sort in order to order different arrays of integers.
These arrays are respectively formed by 100, 1000, 10000, 100000, 200000, 500000 items and can be formed by ordered numbers, partially ordered numbers, inverted ordered numbers and random numbers.
After that I have to calculate the time the algorithm took to order the array.
I have to use recursion, It's a homework.
I created a function that generates the array:
typedef enum {ORINATO, INVERS, PARZ_ORDINATO, RANDOM} Ordine;
int *generaArray(int dimensione, Ordine ordine) {
int i, j, n;
int *array = (int*)malloc(dimensione * sizeof(int));
if (!array){
return NULL;
}
switch (ordine){
case ORINATO:
for (i = 0; i < dimensione; i++){
array[i] = i;
} break;
case INVERS:
n =0;
for ( i = dimensione-1; i >= 0 ; i--) {
array[i] = n;
n++;
}break;
case PARZ_ORDINATO:
for (i = 0; i < dimensione/2 ; i++) {
array[i] = i;
}
for (j = i+1; j <dimensione; j++){
n = rand();
array[j] = n;
};break;
case RANDOM:
for ( i = 0; i <= dimensione ; i++) {
array[i] = rand();
}break;
default:
break;
}
return array;
}
And it works like wonders.
Then I have created the recursive selection sort like follows:
void recursiveSelectionSort(int *array, int dim, int start){
int min=0;
if (start >= dim-1){
return;
}
min = findMin(array, start, start+1, dim);
swap(&array[min], &array[start]);
recursiveSelectionSort(array, dim, start+1);
}
int findMin(int *array, int min, int start, int dim){
if(start == dim ){
return min;
}
if (array[start]< array[min]){
min = start;
}
return findMin(array, min, start+1, dim);
}
void swap (int* x, int *y){
int temp = *x;
x = *y;
y = *temp;
}
Now, this as well should work but something clearly isn't. Let's make an example with the implementation, this is what i put in my main:
int main() {
int *array;
clock_t start, end;
double t;
array = generaArray(1000, ORINATO);
start = clock();
recursiveSelectionSort(array, 1000, 0);
end = clock();
t = ((double) (end - start)) / CLOCKS_PER_SEC;
printf("\nIl tempo impiegato per 1000 elementi รจ: %lf secondi", t);
return 0;
}
This works (but it's slower thank it should be). However if you try and change the dimension from 1000 to 200000 or 500000 it shows error 11.
What is it causing it? I tried everything but it doesn't seem to work.
For starters recursive functions called for large arrays can invoke a stack overflow.
So use non-recursive functions that implement the method selection sort for large arrays.
As for your implementation then for example the function swap has typos.
void swap (int* x, int *y){
int temp = *x;
x = *y;
y = *temp;
}
I think you mean
void swap (int* x, int *y){
int temp = *x;
*x = *y;
*y = temp;
}
All other functions have too many parameters.
For example the function findMin can be declared the following way
size_t findMin( const int *a, size_t n );
and can be also defined as a recursive function (if you decided to write recursive functions then this function can be also recursive)
Here is a demonstrative program that shows how the functions can be defined
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
void swap( int *x, int *y )
{
int temp = *x;
*x = *y;
*y = temp;
}
size_t findMin( const int a[], size_t n )
{
if ( n < 2 )
{
return 0;
}
else
{
size_t i = findMin( a + 1, n - 1 ) + 1;
return a[i] < a[0] ? i : 0;
}
}
void recursiveSelectionSort( int a[], size_t n )
{
if ( !( n < 2 ) )
{
size_t i = findMin( a + 1, n - 1 ) + 1;
if ( a[i] < a[0] ) swap( &a[0], &a[i] );
recursiveSelectionSort( a + 1, n - 1 );
}
}
int main(void)
{
enum { N = 15 };
int a[N];
srand( ( unsigned int )time( NULL ) );
for ( size_t i = 0; i < N; i++ )
{
a[i] = rand() % N;
}
for ( size_t i = 0; i < N; i++ )
{
printf( "%d ", a[i] );
}
putchar( '\n' );
recursiveSelectionSort( a, N );
for ( size_t i = 0; i < N; i++ )
{
printf( "%d ", a[i] );
}
putchar( '\n' );
return 0;
}
The program output might look like
11 9 3 5 6 8 2 4 5 3 7 9 2 0 14
0 2 2 3 3 4 5 5 6 7 8 9 9 11 14