The code:
int main(int argc, char **argv) {
char a[2] = "aa";
printf("%lu\n", strlen(a)); //8
return 0;
}
Why it outputs 8
instead of 2
?
Gcc version:
Configured with: --prefix=/Library/Developer/CommandLineTools/usr --with-gxx-include-dir=/Library/Developer/CommandLineTools/SDKs/MacOSX10.14.sdk/usr/include/c++/4.2.1
Apple LLVM version 10.0.1 (clang-1001.0.46.4)
Target: x86_64-apple-darwin18.7.0
Thread model: posix
InstalledDir: /Library/Developer/CommandLineTools/usr/bin
int main(int argc, char **argv) {
char a[2] = "aa";
printf("%lu\n", strlen(a)); //8
return 0;
}
strlen
requires a zero-terminated string. The 2-element char array a
is not zero terminated, since you didn't provide space for the zero. So strlen
keeps on counting until it runs into a zero somewhere. In your case it happened to be 6 bytes past the end of the a
array. In all cases, access even to one element past the end (i.e. to a[2]
- the third element here) is undefined behavior and may manifest in many more-or-less-entertaining ways (or sometimes hair-rising, too).
There are two fixes (at least), depending on what was your intent:
Make the array at least 3 elements long: it will then fit the zero terminator, and strlen
will be able to stop counting before falling off the end of the array.
Keep the array 2 elements long. But since the array has a fixed size, use sizeof(a)
instead of strlen(a)
. sizeof
determines the size of the array at compile time, since the information about the actual size doesn't really leave the compiler. By the time the program is done compiling and gets to run, it can't safely determine that size anymore - if you keep a
two characters long and use strlen
, that is. Then sizeof
is the only way to provide the program with that information (or by using a magic constant, i.e. sticking another "2" or its equivalent somewhere else).