【发布时间】:2019-06-05 07:10:46
【问题描述】:
编辑:
表达式“30 ? 4 : 1” 和 PHP 中非关联的含义?
已作为副本提供,但这涉及 PHP,而不是 C。
在为一个小程序构建一些测试用例时,我在其中引入了一个错误 for 循环的条件部分,如下所示:
for(int row = 0; row < (mode == TEST) ? NO_OF_TESTS : ROWS; row++){}
(我知道应该将其从for 循环中拉出来,但这不会改变问题。)
这会通过超出数组的末尾作为 以上导致无限循环。
当然,修复很简单:
for(row = 0; row < ((mode == TEST) ? NO_OF_TESTS : ROWS); row++)
// ^ ^
但我对错误实现的行为方式更感兴趣。
这是一段完整的代码(本身没有意义,因为它是 脱离上下文,但它证明了问题)。
#include <stdio.h>
#include <stdlib.h>
#define TEST 0
#define INTERACTIVE 1
#define ROWS 2
#define NO_OF_TESTS 3
#define MAX_FRUIT_LEN 50
int main(void)
{
char test_cases[NO_OF_TESTS][MAX_FRUIT_LEN] =
{{"Orange"},
{"Apple"},
{"Pineapple"}};
int mode = TEST;
int row = 0;
//This fails - but in a strange way
//Uncomment this `for` loop and comment the other one to see the effects
//for(int row = 0; row < (mode == TEST) ? NO_OF_TESTS : ROWS; row++)
//With the parantheses, obviously, it works.
for(row = 0; row < ((mode == TEST) ? NO_OF_TESTS : ROWS); row++)
{
printf("Working:\tIn row %d: Mode: %d condition_eval: %d\n"
, row , mode, row < ((mode == TEST) ? NO_OF_TESTS : ROWS));
printf("Not Working:\tIn row %d: Mode: %d condition_eval: %d\n"
, row, mode, row < (mode == TEST) ? NO_OF_TESTS : ROWS);
printf("Row: %d \tFruit Name: %s\n",row, test_cases[row]);
}
printf("\nTerminating conditional evaluation (at row %d):\n", row);
printf("Working:\tIn row %d: Mode: %d condition_eval: %d\n"
, row , mode, row < ((mode == TEST) ? NO_OF_TESTS : ROWS));
printf("Not Working:\tIn row %d: Mode: %d condition_eval: %d\n"
, row, mode, row < (mode == TEST) ? NO_OF_TESTS : ROWS);
return 0;
}
查看输出和(错误的)条件
row < (mode == TEST) ? NO_OF_TESTS : ROWS
编译器似乎将其解释为:
(row < (mode == TEST)) ? NO_OF_TESTS : ROWS
// ^ ^
问题是:为什么?
这个表达式:
(mode == TEST)
可以被解释为< 运算符的正确操作数,或者
? 运算符的左操作数。 (但我猜不是同时两者。)
适用哪些规则?这是运算符优先级的问题吗?序列点是否起作用? 评估顺序是什么,为什么?
我很困惑;非常感谢任何帮助。
【问题讨论】:
-
@WernerHenze:不要考虑将 PHP 骗子链接到 C 问题。 PHP 家伙决定反转三元条件运算符的关联性!
-
不要在 for 循环的控制子句中编写 icky 运算符 goo,而是编写可读代码:
int max = something; for(int row = 0; row<max; row++) { ... max = (mode == TEST) ? NO_OF_TESTS : ROWS } -
"这是运算符优先级的问题吗?" 为什么不直接在任何 C 书籍中查找呢?例如这里:en.cppreference.com/w/c/language/operator_precedence
-
@Lundin True。我实际上是在我原来的帖子里写的。没有更改代码,因为它对问题没有任何影响。
-
@Bathsheba 好点。那我们就拿这个吧:stackoverflow.com/questions/25598884/…
标签: c ternary-operator operator-precedence