if条件中的多个条件
如果我有一个if语句需要满足这些要求:
if(cave > 0 && training > 0 && mobility > 0 && sleep > 0)
有什么方法可以说,他们都大于零? 只是为了更有效的干代码?
就像是:
if(cave, training, mobility, sleep > 0)
你可以用Math.min得到最低的值,然后你只需要对下限进行一次检查。
if(Math.min(cave, training, mobility, sleep) > 0) { //do something }
你可以使用.every数组。 这是干的less,但更详细:
var isGreaterThanZero = function(val) { return val > 0; }; if([cave, training, mobility, sleep].every(isGreaterThanZero)) { // Do Something }
我喜欢这个的原因是通过使用一个数组,显然你正在为每个variables重复逻辑。 以明显的方式命名callback可以帮助未来的读者准确理解检查的内容。 最后,这不仅为数字提供了范围,而且在未来对任何types的任何检查都有了范围 – 复杂性远远超出if
语句本身。
正如有些人所说,在if语句中有多个简单的条件没有什么不对,但是我会考虑将格式更改为:
if ( cave > 0 && training > 0 && mobility > 0 && sleep > 0 )
或者我会改变使用这些variables作为整数,变成布尔variables,即isCave
, hasTraining
,或类似,然后设置适当的布尔更接近你的代码定义不同的属性( 编辑:如果是假,以防止进一步的不必要的计算)。 这将在下一个代码块中简化对后者的if语句,此外,如果条件稍微复杂一些,或者您想要简化if语句的读取,则会显示一个可以使用的变体:
var isCave = cave > 0; # What does cave > 0 mean? var hasTraining = training > 0; var isMobile = mobility > 0; var isNotSleeping = sleep > 0; # What does sleep > 0 indicate? Unclear if (isCave && hasTraining && isMobile && isNotSleeping ) { // Do your thing }
换句话说,if语句中的多个条件并不是你最大的代码味道,我将把焦点转移到给你的variables更好的名字上,清楚地指出这个值的含义。 这样可以提高对代码的阅读和理解,而不仅仅是一些奇怪的语法,以避免多个条件。
在if
语句中有多个简单的条件没有任何问题。 但是,如果它不能适合一行(大约80个字符),你有几个解决scheme。
最终,你不检查四个variables是否大于零。 您正在检查一组条件。 这些条件( 当前 )由有符号整数表示的事实不仅是不相关的,而且是应该隐藏在函数中的实现细节。
-
使用中间标志:
var valid_location = false; if (cave > 0 && training > 0) valid_location = true; var valid_status = false; if (mobility > 0 && sleep > 0) valid_status = true; if (valid_location && valid_status) // ...
-
使用function:
function can_do_this() { // split conditions into logical groups // checking location, because you need training if you're // in a cave if (cave <= 0 || training <= 0) return false; // checking status, because you have to be mobile and // sleepy if (mobility <= 0 || sleep <= 0) return false; return true; } if (can_do_this()) // ...
-
使用您需要检查的个别条件的function:
function valid_location() { return (cave > 0 && training > 0); } function valid_status() { return (mobility > 0 && sleep > 0); } if (valid_location() && valid_status()) // ...
听起来像一个像这样的“validation器”function的工作:
function areAllGreaterThanZero(){ //TODO: check inputs var result = true; [].splice.apply(arguments).forEach(function(x){ result = result && (x > 0); }); return result; } if(areAllGreaterThanZero(cave, training, mobility, sleep)) { // ... }
正如其他人所build议的那样,如果您不介意使用ES6或polyfills,则可以使用.every:
var hasAllStats = [cave, training, mobility, sleep] .every(function(stat) { return stat > 0; }); if (hasAllStats) { }
或者,您可以使用.some来获得反转(也需要ES6或polyfill):
var isMissingStats = [cave, training, mobility, sleep] .some(function(stat) { return stat <= 0; }); if (!isMissingStats) { }
如果你不想使用ES6,你可以使用reduce:
var hasAllStats = [cave, training, mobility, sleep] .reduce(function(hasAllStats, stat) { return hasAllStats && stat > 0; }, true); if (hasAllStats) { }
假设32位整数。
if ((cave | training | mobility | sleep) > 0)
如果上述任何一个数字是负数,则OR的结果将是负数,并且不符合要求。
编辑:当任何一个参数都是0时,它不起作用。这将起作用,但不会像其他方式那样高效且容易阅读。
if (((cave | training | mobility | sleep) > 0) && (cave*training*mobility*sleep != 0))
另一个更好的修复
if (!((cave | training | mobility | sleep) < 0))
用lodash过滤:
var data = [cave, training, mobility, sleep]; var result = _.filter(data, function (datum) { return datum > 0; }).length === data.length; console.log(result);
它对数组元素进行迭代,并返回由满足给定要求> 0
的那些元素组成的新数组。如果结果数组的大小不同于给定的大小,则意味着它的一个或多个元素不是> 0
。
我特地写了它来检查每个数组的值(即使没有必要,因为第一个> 0
可能会给出相同的结果)不停止在第一个积极的,因为你说你想检查所有这些。
PS你可以反转它来检查<= 0
并检查.length === 0
instaed更快。
为什么你正在寻找解决scheme?
你的问题看起来像最好和简单的答案,我推荐它。 我们有多种解决scheme。 下面是一个。
JSBin for .every()
通过使用.everyfunction来实现
var flag = [cave, training, mobility, sleep].every(function(val) { return val > 0; }); if(flag) { alert('All the elements are greater than Zero'); }