这是未定义的行为吗? (因为字符串“True”,“False”和“Error”仅在块内退出并在退出块时被销毁):
char *p;
if (var1) {
p = "True";
} else if (var2) {
p = "False";
} else {
p = "Error";
}
printf("%s\n", p);
我认为这同样适用于switch语句。那么我怎么能表达上面的逻辑呢?
子问题: 这也是未定义的行为吗? :
struct bar {
int i;
double d;
}
struct bar *barptr;
if (var1){
barptr = &(struct bar) { 0, 0.0 };
} else {
barptr = &(struct bar) { 5, 40.3 };
}
printf("%d", barptr->i);
答案 0 :(得分:5)
没有任何未定义的行为。字符串文字具有静态存储持续时间。 只有无效代码(在编辑帖子之前),因为您忘记在语句中指定条件
else if
根据C标准(6.4.5字符串文字)
6在转换阶段7中,附加一个值为零的字节或代码 每个由字符串文字产生的多字节字符序列 或者文字.78)然后使用多字节字符序列 初始化一个静态存储持续时间和长度的数组 足以包含序列
至于复合文字,那么代码片段确实有未定义的行为。根据C标准(6.5.2.5复合文字)
5复合文字的值是未命名对象的值 由初始化列表初始化。如果出现复合文字 在函数体外,该对象具有静态存储 持续时间; 否则,它具有相关的自动存储持续时间 封闭区块。
考虑到必须有
barptr = &(struct bar) { 0, 0.0 };
如果您要编写
,代码段将是有效的struct bar {
int i;
double d;
};
struct bar bar;
if (var1){
bar = (struct bar) { 0, 0.0 };
} else {
bar = (struct bar) { 5, 40.3 };
}
printf("%d", bar.i);
答案 1 :(得分:1)
至于此代码段'关注,没有问题。 (从代码中删除了无用/不完整的if else检查:-))
int main ()
{
char *p;
int var = 0;
if (var){
p = "True";
} else {
p = "False";
}
printf("%s\n", p);
return 0;
}
如果var = 0,它将打印" False"否则它将打印" True"。
答案 2 :(得分:1)
字符串文字具有静态存储持续时间。
6.4.5。 p6在转换阶段7中,将值为零的字节或代码附加到每个多字节 由字符串文字或文字产生的字符序列.78)多字节字符 然后,序列用于初始化静态存储持续时间和长度的数组 足以包含序列。
静态存储持续时间意味着变量在程序启动时初始化,并在整个程序中有效。
您的第一个示例没有未定义的行为。
但是在第二个示例中,您尝试指向具有自动存储持续时间的复合文字,这意味着一旦退出if语句,它们就不再存在。
6.5.2.5。 p5复合文字的值是由初始化的未命名对象的值 初始化列表。如果复合文字出现在函数体外,则为对象 有静态存储时间;否则,它与自动存储持续时间相关联 封闭的块。
struct bar *barptr;
if (var1){
barptr = &(struct bar) { 0, 0.0 };
} else {
barptr = &(struct bar) { 5, 40.3 };
}
barptr->i = 123 ; //UNDEFINED BEHAVIOR
答案 3 :(得分:0)
通常,字符串文字(“True”和“False”)将存储在数据部分的只读页面中
所以它不是未定义的行为。
答案 4 :(得分:0)
这是明确的定义。按标准:
6.4.5字符串文字
语法
[...]
描述
2字符串文字是包含在其中的零个或多个多字节字符的序列 双引号,如“xyz”。宽字符串文字是相同的,除了前缀 信L。
所以你的作业是stringliterals。关于Stringliterals的使用寿命ISO / IEC 9899:TC3说:
[...]
5在转换阶段7中,将值为零的字节或代码附加到每个多字节 由字符串文字或文字产生的字符序列。多字节字符 然后,序列用于初始化静态存储持续时间和长度的数组 足以包含序列。
因此,您可以看到从程序的开始到终止存在字符串文字。
现在你也知道他们就是这样的“字符串文字”
所以你可以肯定。
绝对定义明确。
答案 5 :(得分:-2)
这是未定义的行为吗? (因为字符串“True”,“False”和“Error”仅在块内退出并在块退出时被销毁)
没有。你应该看看变量,而不是文字。在char* p
中调用时,printf
存在。