如果条件条件,最可读的方法是长时间格式化的方法? [关闭
https://softwareengineering.stackexchange.com/questions/3450
-
16-10-2019 - |
题
长曲折 if
如果可能的话,应避免条件,但有时我们最终都会写它们。即使这是一个非常简单的条件,涉及的陈述有时简直是非常勇敢的,因此整个条件最终会非常漫长。格式化这些最可读性的方法是什么?
if (FoobarBaz::quxQuux(corge, grault) || !garply(waldo) || fred(plugh) !== xyzzy) {
thud();
}
或者
if (
FoobarBaz::quxQuux(corge, grault)
|| !garply(waldo)
|| fred(plugh) !== xyzzy
) {
thud();
}
或者
if (FoobarBaz::quxQuux(corge, grault)
|| !garply(waldo)
|| fred(plugh) !== xyzzy) {
thud();
}
或者
thudable = FoobarBaz::quxQuux(corge, grault);
thudable ||= !garply(waldo);
thudable ||= fred(plugh) !== xyzzy;
if (thudable) {
thud();
}
还是其他偏好?
解决方案
通常,如果条件是需要重构的代码的符号,但有时您无法避免。在这种情况下,我更喜欢第一个:
if (bar || baz || quux) { ... }
因为您可以告诉一行发生了什么。但是,我宁愿在可能的情况下做这样的事情:
function foo() {
return bar || baz || quux;
}
if (foo()) { ... }
其他提示
我喜欢让操作员结束以表示延续:
if (the_function_being_called() != RETURNCODE_SUCCESS &&
the_possibly_useful_recovery_strategy() == RETURNCODE_EPICFAIL &&
this_user_has_elected_to_recieve_error_reports)
{
report_error();
}
我是有意义的变量名称的忠实拥护者:
const bool isInAStrangeCondition =
FoobarBaz::quxQuux(corge, grault) ||
!garply(waldo) ||
fred(plugh) !== xyzzy;
if (isInAStrangeCondition) {
thud();
}
或重构作为功能,如上所述。
我将杂乱的子表达式或全部分解为bool变量。然后可以清楚地表明“ if”语句的顶级布尔逻辑。在我所做的那种工作中,这并不总是有几件事。
bool goodblah = some_mess < whatever;
bool frobnacious = messy_crud != junky_expression;
bool yetanother = long_winded_condition;
if (goodblah || (frobnacious && yetanother)) {
...
}
这在调试器中特别好,在执行“如果”之前,我可以在其中查看所有布尔。
我倾向于在新线路开始时对齐运算符,因此我记得如何将术语(无论是长长的逻辑还是长期算术)结合起来。像这样:
if (first_attempt(data) == SUCCESS
|| (reusable(data) && second_attempt(data) == SUCCESS)
|| (still_reusable(data) && third_attempt(data) == SUCCESS))
return SUCCESS;
这仅在我按2个空间缩进或设置我的环境以缩进多行谓词时才能起作用,否则很难分辨出谓词结束和有用的代码从哪里开始。
我是以下粉丝:
if (really_long_expression && another_really_really_long_expression &&
another_very_long_expression_OMG_id_it_long){
bugs();
}
这样,它仍然看起来像是一个if表达,而不是表达式的破碎。凹痕有助于表明这是上一行的延续。
您也可以将其缩进,直到开放式支架位于上一行的末尾,以便它位于IF表达式的末尾。