I'm currently studying c array and is confused about what can and can't be used to represent the size of the array during initialisation.
Am I right to assume
#define SIZE 5
and
const int SIZE = 5;
are fundamentally different to one another?
They have their difference and one particular example that confuses me is
#define SIZE 5
int arr[SIZE] = {11, 22, 33, 44, 55};
is valid syntax, but
const int SIZE = 5;
int arr[SIZE] = {11, 22, 33, 44, 55};
is not valid syntax. Though interestingly,
const int SIZE = 5;
int arr[SIZE];
is valid syntax.
What's the logic behind whether a particular syntax is valid or invalid?
The following syntax uses a “for loop” to initialize the array elements. This is the most common way to initialize an array in C. // declare an array. int my_array[5];
To initialize or instantiate an array as we declare it, meaning we assign values as when we create the array, we can use the following shorthand syntax: int[] myArray = {13, 14, 15}; Or, you could generate a stream of values and assign it back to the array: int[] intArray = IntStream.
Single Dimensional Array Initialization. The process of assigning values to the array elements is called array initialization. Once an array is declared, its elements must be initialized before they can be used in the program. If they are not properly initialized the program produces unexpected results.
Am I right to assume
#define SIZE 5
and
const int SIZE = 5;are fundamentally different to one another?
Yes, you are right.
#define
is simply a textual replacement. Basically, the C preprocessor is going a "find and replace" for you during the compilation process (processing stage). Whereas, const
qualified object means "the thing stored at this location can't changed" - roughly equivalent to saying it's "read-only".
#define SIZE 5
int arr[SIZE] = {11, 22, 33, 44, 55};is valid syntax.
This is exactly equivalent to writing:
int arr[5] = {11, 22, 33, 44, 55};
yourself. The compiler simply does the replacement job for you when you use define
.
const int SIZE = 5;
int arr[SIZE] = {11, 22, 33, 44, 55};
is not valid syntax.
It's invalid but the reason could be more than one. If arr
has static storage duration (i.e., the object arr
is alive throughout the program execution) then it's invalid. Because C requires that the size of an array object with static storage duration to be a constant expression:
If the size is an integer constant expression and the element type has a known constant size, the array type is not a variable length array type; otherwise, the array type is a variable length array type.
So, the following program is not valid:
const int SIZE = 5;
int arr[SIZE] = {11, 22, 33, 44, 55};
int main(void)
{
}
because SIZE
doesn't qualify as a "constant expression" in C. Note that this is totally valid in C++ where SIZE
qualifies as a constant expression (the two languages differ here).
Another reason is C standard doesn't allow initializing variable-length arrays. If you have the definition inside a function such as:
The type of the entity to be initialized shall be an array of unknown size or a complete object type that is not a variable length array type.
So if you don't have the initializer then it becomes valid:
int main(void)
{
const int SIZE = 5;
int arr[SIZE]; /* This is OK */
}
Similarly, you can do without the const
as well:
int main(void)
{
int SIZE = 5;
int arr[SIZE]; /* Thi is OK too. */
}
In both of the above snippets, arr
is simply a variable-length array.
Though interestingly,
const int SIZE = 5; int arr[SIZE];
is valid syntax.
It's valid only if it's inside a function (as above) - it's a VLA. But if you make it have static storage duration such as:
const int SIZE = 5;
int arr[SIZE]; /* arr has static storage duration just as
all objects defined at file scope */
int main(void)
{
}
it's invalid because as noted above, SIZE
is not a "constant expression" in C.
Similarly,
int main(void)
{
const int SIZE = 5;
static int arr[SIZE]; /* arr has static storage duration */
}
is invalid for the same reason, despite arr
being inside a function, because arr
has static storage duration.
However, if you have:
enum {SIZE = 5};
int arr[SIZE] = {11, 22, 33, 44, 55};
int arr2[SIZE]; /* Valid without initializer too. */
int main()
{
}
it's valid. Why? Because enum constants qualify as "constant expressions" in C.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With