This is a compiler- and option-specific effect.
Static variables are zero-initialized first of all. Automatic local variables have no such guaranteed initialization. But a compiler can add zero-initialization, just to be “helpful”.
You're accidentally right that for the presented code the 0 result is “the consequence of undefined behavior”. But that's only because using an indeterminate value of type int
is undefined behavior, or at least was UB up till and including C++11. It's a bit unclear whether accessing an indeterminate value of one of the three basic char
types is UB: there are some Defect Reports about it (DR #240 and #616), and the C++14 wording is different from C++11 and earlier, and seems to have moved the specification of UB to some other part of the standard.