2

I am implementing program to count frequency of digits in alphanumeric string, but after spending hours with weird output I am able to find solution that C is setting garbage value to all index values. But surprise for me is that compiler setting some values to zero(in my example it is setting 0 for 0 to 7 index, and some random garbage value at 8th and 9th position). Still, after searching around so much and discussion with colleague, I am not find any solution.

Here I am posting my code and output.

#include <assert.h>
#include <limits.h>
#include <math.h>
#include <stdbool.h>
#include <stddef.h>
#include <stdint.h>
#include <stdio.h>
#include <stdlib.h>

#define MAX_LENGTH  1000

int main()
{
    int ar[10];

    char s[MAX_LENGTH];
    scanf("%s",s);

    for(int i = 0; i < strlen(s); i++){
        int index = s[i] - 48;
        if(index >= 0 && index <= 9){
            ar[index] = ar[index] + 1;
        }
    }

    for(int i = 0; i <= 9; i++){
        printf("%d \n", ar[i]);
    }
}

Input : as12556fsd889ad9

From debugger I am getting this snap shot : debugger snap shot

Output :

0 
1 
1 
0 
0 
2 
1 
0 
1606415986 
32769

Why compiler setting garbage value 0 from index 0 to 7 and 1606415986 at index 8 and 32769 at index 9.

Any help or link which give me deep understanding for this would be appreciated.

I am beginner and student so please do not down vote my question. Thanks

  • 1
    C does not set the values of local variables, including arrays. You must set them yourself. The compiler should warn you about using an uninitialised variable. This saves execution time in the cases where you write to a variable before it is read. – Weather Vane Jun 14 '18 at 16:03
  • 1
    Variables with automatic storage class (read - local variables) are not initialized by the runtime. These questions are not answered by discussions but by reading documentation. – Eugene Sh. Jun 14 '18 at 16:04
  • Uninitialized variables on the stack start off with indeterminate values until you assign them. Assigning a value to an element of an array will not magically initialize the elements that haven't been assigned to yet. – Ian Abbott Jun 14 '18 at 16:05
  • Thanks for response but why it setting first 8 values to `0` and then random value ? – nisheethposhiya Jun 14 '18 at 16:05
  • It isn't setting them: those are the values that happpened to be in memory. – Weather Vane Jun 14 '18 at 16:06
  • it's not setting anything,, those just happen to be the residual values in memory from whatever was there before. The bits have to be _something_, 1 or 0, there's no third state signifying an uninitialized value. – yano Jun 14 '18 at 16:06
  • If you don't initialize a variable then it's not initialized, meaning that the contents of that variable will be whatever the memory for that variable happened to have in it. – Bob Jarvis - Слава Україні Jun 14 '18 at 16:08
  • Thanks for all of you for input. Will see in details. Please share some link if any of you have, how memory allocation works? – nisheethposhiya Jun 14 '18 at 16:16
  • Aside: Consider `for(int i = 0; i < strlen(s); i++){` --> `for(int i = 0; s[i]; i++){` as it is significant more efficient with a compiler that does not optimize. – chux - Reinstate Monica Jun 14 '18 at 16:37
  • Aside: `int index = s[i] - 48; if(index >= 0 && index <= 9){ ar[index] = ar[index] + 1;` could be replaced with `if(index >= '0' && index <= '9'){ index -= '0'; ar[index] = ar[index] + 1;`. That is more portable and avoids the magic number 48. – chux - Reinstate Monica Jun 14 '18 at 16:40

3 Answers3

4

int ar[10]; inside a function does not initialize the elements to 0. ar is uninitialized.

The value of the elements of ar[] are indeterminate. @haccks

The compiler may set them to 0, may set them to "garbage", stop code if accessed and it contains a trap value, or many others possibilities. The most likely scenario is that the values are whatever happens to be in memory.

The point is that good code should first initialize them or assign them, before reading them.

// char s[MAX_LENGTH];
char s[MAX_LENGTH] = { 0 };
haccks
  • 104,019
  • 25
  • 176
  • 264
chux - Reinstate Monica
  • 143,097
  • 13
  • 135
  • 256
2

While is is not mandatory to initialize arrays in C, one should not use uninitialized values at all. The array ar in your code has automatic storage, so it is uninitialized. Since your code relies on the fact that the initial values are zero, you must initialize it explicitly with int ar[10] = { 0 };

Note that if this array was defined as a global variable, it would be initialized to 0, but if you were to allocate it with malloc() it would be uninitialized. It cannot hurt to always initialize your variables.

Note also that you should test the return value of scanf() and pass the maximum number of characters to store into the destination array:

if (scanf("%999s", s) != 1) {
    printf("input error\n");
    return 1;
}
chqrlie
  • 131,814
  • 10
  • 121
  • 189
1

If you want them to have a predictable initial value, then yes.

int ary[10] = {0};

will initialize them all to zero

EvilTeach
  • 28,120
  • 21
  • 85
  • 141