Variable Initialization in C++

Initializing variables in C

A rule that hasn't been mentioned yet is this: when the variable is declared inside a function it is not initialised, and when it is declared in static or global scope it's set to 0:

int a; // is set to 0

void foo() {
int b; // set to whatever happens to be in memory there
}

However - for readability I would usually initialise everything at declaration time.

If you're interested in learning this sort of thing in detail, I'd recommend this presentation and this book

when is initialization for variables required in C programming

The only constraint in C is objects must be initialized before you can read their value.

Global objects and local objects with static storage class are initialized automatically when the process is started, either from the explicit initializer you wrote in the source code in their definition, or to their zero value (and that of all of their members and elements for aggregates) if no initializer is present at the definition point in the source code. The zero value is 0 for numeric and character types and NULL for pointers. The first member of unions is initialized to its zero value.

Other local objects are not initialized by default, so you must either provide an initalizer at the point of definition or store a value into them before you read their value.

In your example, in the while loop, the values of ch2 and ch3 are read before they are written to. These must be initialized before the loop, but a value is stored into ch and ch1 before the if, so they do not need to be initialized before the loop. You could safely remove the initializer for ch1.

The reason the compiler warns you to initialize ch2 and ch3 is to avoid undefined behavior during the first iteration of the loop. If by chance uninitialized ch2 had the value 'h' and uninitialized ch3 had the value 'e' before the first iteration, just hitting y would suffice to break from the loop.

I urge you to compile your code with warnings enabled to allow the compiler to diagnose potential uses of uninitialized variables. It is not perfect, there can be both false positives and false negatives, but the diagnostics are usually very useful to avoid silly mistakes leading to undefined behavior.

It does not hurt to initialize all local variables to a constant. The compilers are usually smart enough to remove redundant stores, ie: they do not generate code for storing values to non volatile local variables that are not used before either receiving another value or going out of scope.

Note that your code can be simplified with one less variable this way:

#include <stdio.h>
#include <conio.h>

int main(void) {
int ch = 0, ch1 = 0, ch2;
for (;;) {
ch2 = ch1;
ch1 = ch;
ch = _getche();
if (ch2 == 'h' && ch1 == 'e' && ch == 'y') {
break;
}
}
printf("\nHello !\n");
return 0;
}

When are local variables initialized in C?

In practice, a variable will be initialized before use, regardless if it is placed in an inner scope or not. This code:

void func1 (int i){
if(i) {
int arr[2048] = {0};
printf("%d", arr[666]);
} else {
//Doing something
}
}

gives exactly the same machine code as this code:

void func2 (int i){
int arr[2048] = {0};
if(i) {
printf("%d", arr[666]);
} else {
//Doing something
}
}

gcc -O3 on x86 gives:

.LC0:
.string "%d"
func1:
test edi, edi
jne .L4
ret
.L4:
xor esi, esi
mov edi, OFFSET FLAT:.LC0
xor eax, eax
jmp printf

and

.LC0:
.string "%d"
func2:
test edi, edi
jne .L7
ret
.L7:
xor esi, esi
mov edi, OFFSET FLAT:.LC0
xor eax, eax
jmp printf

As you can see they are identical.

It is good design practice to limit the scope of variables as much as possible though, but that has nothing to do with performance.

Always initialize variables in C

Some programmers say that you should always declare all variables in a beginning of a sequence (function) first in C ...

I find declaring variables close to where there are used first is better. @pm100

Yet this is a style issue. Best to follow your group's coding standard.

Is it also a good idea to initialize all variables at the beginning or is it a waste of processor time?

With simple variables this is not a "waste of processor time".

With long arrays, there is a small chance of significant delay.

#define N 4096
char buf[N];
// or
char buf[N] = { 0 };
if (fread(buf, sizeof buf[0], N, ...

Perform "unneeded" initialization per your group's coding standard.

Consider 4 cases: 3 have potential UB

// No initialization
char buf1[N];
fgets(buf1, sizeof buf1, stdin);
fputs(buf1, stdout);

// Initialization
char buf2[N] = {0};
fgets(buf2, sizeof buf2, stdin);
fputs(buf2, stdout);

// No initialization, early assignment
char buf3[N];
buf3[0] = '\0';
fgets(buf3, sizeof buf3, stdin);
fputs(buf3, stdout);

// No initialization, test function result that populates buf4
char buf4[N];
if (fgets(buf4, sizeof buf4, stdin)) {
fputs(buf4, stdout);
}

Only if (fgets(buf4, sizeof buf4, stdin)) is proper protection against a read error which ends with "the array contents are indeterminate".

I neither critique for nor against unnecessary initialization as 1) compilers often (not always) detect and warn about missing initialization/assignment 2) Coding problems I see tend to exist in not examining error status and 3) as with holy war issues like Indent style this, I follow my group's coding standard - whatever it is.

Why does this C code take so long to compile and execute if the variable is not initialized?

The scanf is failing. Check the return value.

i.e.

   if (scanf("%d", &max) != 1) {
fprintf(stderr, "Unable to read max");
exit(1);
}

max is probably some large value hence the large amount of time

EDIT

The delay to see the prompt is that the printf is in a buffer and will not be displayed until the loop completes

In C, multiple initialization of a variable is not throwing an error. Why?

Multiple initialization will throw error only if the variable is constant.
Not-constant variables can be initialized multiple times.

U can use

const int x=0

So that multiple initialization will not be allowed.



Related Topics



Leave a reply



Submit