问题描述
澄清:
这纯粹是为了实验目的,学习一门新的(对我来说)语言的怪癖、零碎和结束。如果我要与其他人分享这段代码,我当然会把它写成可读的。 :-)
我有一个函数 someFunction(x)
和两个全局变量:
let m = 2;
let e = 5;
在函数内部,我想检查是否x == m
。如果这是真的,我想将 m
传递给辅助函数调用 (sidefunction(m)
),然后将 x
重新分配给 e
以完成 someFunction
。
这确实按预期工作:
const someFunction = x => {
if (x == m) {
sidefunction(m);
x = e;
}
doOtherStuffWith(x);
}
但是,我想缩短它,最好是一行。这也是为了更多地了解三元和/或布尔链。
这两种方法我都试过了:
// Boolean chaining
const someFunction = x => {
x == m && sidefunction(m) && (function () {x = e})();
doOtherStuffWith(x);
}
这没有工作,大概是因为赋值 x = e
仅适用于内部匿名函数的局部范围内的 x
...?
// Ternary operator
const someFunction = x => {
x = (x == m && sidefunction(m)) ? e : x;
doOtherStuffWith(x);
}
这没有工作,大概是因为sidefunction(m)
实际上没有被调用,出于某种原因......?
如何修复这些问题以使其正常工作?
或者,是否有其他优雅的方法可以在没有完整的多行 if
块的情况下执行此检查/调用/重新分配?
非常感谢!
解决方法
问题
x == m && sideFunction(m) && (function () {x = e})();
是 &&
从左到右计算,一旦找到第一个 falsey 值就会停止。除非 sideFunction
返回明确的真值,否则第三个 IIFE:
(function () {x = e})()
永远不会运行,导致 x
永远不会被重新分配。
x
在该函数中是局部的。如果您可以运行该函数,它将根据需要重新分配 x
。
您可以使用逗号运算符:
x == m && (sideFunction(m),x = e);
同样
x = (x == m && sideFunction(m)) ? e : x;
不会工作,因为 sideFunction
必须返回一些真实的东西才能让条件的左侧真实地评估 - 否则,x
将被分配给 x
,没有变化。
所有这些都说了 - 我强烈建议不要做任何这些。您的第一种方法更具可读性,可读性比行保持重要得多。
,您可以使用带有 comma operator 的复合表达式,而不必关心 sideFunction
的结果值。
const fn = x => (x == m && (sideFunction(m),x = e),doOtherStuffWith(x));
,
逗号运算符 ,
可用于链接表达式并返回最后一个,例如,
var x = (1 + 2,10 + 2,100 + 2);
x;
//=> 102
我们可以用它来计算 sideFunction(m)
并返回 e
:(sideFunction(m),e)
。
既然你总是想执行doOtherStuffWith
,你只需要弄清楚是给它e
还是原来的x
:
const someFunction = x => doOtherStuffWith(x == m ? (sideFunction(m),e) : x);