lqdc
lqdc

Reputation: 531

trouble with pointers in C

So I have this code:

#include <stdio.h>
int arraySum (int *a, int n);
int main(void){
    int values[3] = {1, 2, 3};
    printf("The sum is %i\n", arraySum(values, 3));
    return 0;
}
int arraySum(int *a, int n){
    int sum = 0;
    int arrayEnd = *a + n;
    for ( ; *a < arrayEnd; *a++)
        sum += *a;
    return sum;
}

For some reason it outputs this:

roman@lmde64 ~/Dropbox/Practice $ gcc practice.c 
roman@lmde64 ~/Dropbox/Practice $ ./a.out
The sum is -421028781
roman@lmde64 ~/Dropbox/Practice $ ./a.out
The sum is -362865581
roman@lmde64 ~/Dropbox/Practice $ ./a.out
The sum is -1046881197
roman@lmde64 ~/Dropbox/Practice $ ./a.out
The sum is 6
roman@lmde64 ~/Dropbox/Practice $ ./a.out
The sum is 6

Why is the output strange numbers sometimes and the right answer other times? What am I doing wrong? Thanks for any help.

Upvotes: 5

Views: 206

Answers (5)

Nallu
Nallu

Reputation: 106

In the original code,

  • *a + n evaluates to 1+3 = 4
  • In every iteration of the for loop , the value pointed to by *a is compared with 4.
  • If the value *a is less than 4, then the sum is computed.
  • After 3 iterations, a is pointing to values[2] which is 3. Later, when a is incremented, it points to the address beyond value[2] -- this address can contain any garbage value. If the garbage value is less than 4, it will compute sum. This behavior continues until a value greater than 4 is encountered. Hence the value of sum is sometimes 6 or some other garbage value

Upvotes: 1

Richard Schneider
Richard Schneider

Reputation: 35464

int arraySum(int *a, int n) {
   int sum = 0;
   for (int i = 0; i < n; ++i)
      sum += a[i];
   return sum;
}

or

int arraySum(int *a, int n) {
   int sum = 0;
   for (int i = 0; i < n; ++i)
      sum += *a++;
   return sum;
}

Upvotes: 1

pmg
pmg

Reputation: 108986

  • *a++ is the same as *(a++); the * does nothing in this instance
  • arrayEnd gets set to *a + 3, or 1 + 3, or 4
  • your for loop does not terminate before the array is exhausted. Accessing outside the array limits invokes undefined behaviour
  • your program could just as well have output "The mighty sum is not what you expect!\n"

Upvotes: 1

Erik
Erik

Reputation: 91330

You want to iterate over the array:

int arraySum(int *a, int n){
    int sum = 0;
    int * arrayEnd = a + n; // arrayEnd points to the first element after your array a
    for ( ; a != arrayEnd; ++a)  // Iterate over the array until you reach arrayEnd
        sum += *a; // Dereference the pointer to current array element in order to retrieve a value
    return sum;
}

Upvotes: 2

Oliver Charlesworth
Oliver Charlesworth

Reputation: 272812

In arraySum(), you are confusing when to use a as a pointer, and when to dereference it to obtain what it is pointing to. When you are calculating the loop limits, etc., you want to be working with the pointer itself:

int arraySum(int *a, int n){
    int sum = 0;
    int *arrayEnd = a + n;
    for ( ; a < arrayEnd; a++)
        sum += *a;
    return sum;
}

Upvotes: 14

Related Questions