Javascript 空检查性能(比较 if 和 try/catch)
Javascript null check performance (compare if and try/catch)
我必须获取内部组件的值。仅针对性能进行比较时,1 或 2 哪个更好,此方法被调用了多次。 foo 可能为空,具体取决于运行时,但 foo 可能有值,但 bar 可能有null 等。 foo、bar、innerfoo、innerbar 中的任何一个为空都不是错误情况或意外情况,它们中的任何一个都可以在运行时为空,具体取决于层次结构。但如果 foo 为 null,innerbar 不能有任何值,因此如果 foo 未定义,则无需检查内部组件。
//1
function getInnerValue() {
if (foo && foo.bar && foo.bar.innerfoo && foo.bar.innerfoo && foo.bar.innerfoo.innerbar) {
return foo.bar.innerfoo.innerbar.x;
}
return 0;
}
//2
function getInnerValue() {
try {
return foo.bar.innerfoo.innerbar.x;
}
catch (e) {
return 0;
}
}
任何带有触发的 try catch 都会对性能造成很大影响。
就我个人而言,我并不认为长链的真值检查比 try catch 块的可读性差。只是更长,丑陋和冗长。但实际上,有人会在阅读(或编辑)时遇到困难吗?或者更好的说法是,您甚至需要阅读它才能理解它在做什么吗?
事实上,try catch 块感觉更像是一个 hack。还得想一想为什么要抓异常,还是丑。
无论如何,我们现在有了可选链接,所以上面的内容甚至不再重要了。我会选择 return x?.y?.z?.a?.b?.c?.d||0
.
您当然可以使用保护函数,因为您可能已经注意到阅读您所链接的线程。像 lodash _.get
或者你自己的 guard(a,'b','c','d').
optional chaining browser compatibility
Babel transpiled output of optional chaining
x?.y
将立即 return undefined
如果 x 为空或未定义
浏览器兼容性相对较新。检查 table 兼容性。您应该将 Babel 转译添加到您的管道中。
不带转译的可选链接:
foo = {}
function fn() {
if (foo?.bar?.innerfoo?.innerbar)
return foo.bar.innerfoo.innerbar.x
return 0
}
console.log(fn())
foo = {bar: { innerfoo: { innerbar: { x: 5 }}}}
console.log(fn())
转译代码:
foo = {}
function fn() {
var _foo, _foo$bar, _foo$bar$innerfoo;
if ((_foo = foo) === null || _foo === void 0 ? void 0 : (_foo$bar = _foo.bar) === null || _foo$bar === void 0 ? void 0 : (_foo$bar$innerfoo = _foo$bar.innerfoo) === null || _foo$bar$innerfoo === void 0 ? void 0 : _foo$bar$innerfoo.innerbar) return foo.bar.innerfoo.innerbar.x;
return 0;
}
console.log(fn())
foo = {bar: { innerfoo: { innerbar: { x: 5 }}}}
console.log(fn())
我必须获取内部组件的值。仅针对性能进行比较时,1 或 2 哪个更好,此方法被调用了多次。 foo 可能为空,具体取决于运行时,但 foo 可能有值,但 bar 可能有null 等。 foo、bar、innerfoo、innerbar 中的任何一个为空都不是错误情况或意外情况,它们中的任何一个都可以在运行时为空,具体取决于层次结构。但如果 foo 为 null,innerbar 不能有任何值,因此如果 foo 未定义,则无需检查内部组件。
//1
function getInnerValue() {
if (foo && foo.bar && foo.bar.innerfoo && foo.bar.innerfoo && foo.bar.innerfoo.innerbar) {
return foo.bar.innerfoo.innerbar.x;
}
return 0;
}
//2
function getInnerValue() {
try {
return foo.bar.innerfoo.innerbar.x;
}
catch (e) {
return 0;
}
}
任何带有触发的 try catch 都会对性能造成很大影响。
就我个人而言,我并不认为长链的真值检查比 try catch 块的可读性差。只是更长,丑陋和冗长。但实际上,有人会在阅读(或编辑)时遇到困难吗?或者更好的说法是,您甚至需要阅读它才能理解它在做什么吗?
事实上,try catch 块感觉更像是一个 hack。还得想一想为什么要抓异常,还是丑。
无论如何,我们现在有了可选链接,所以上面的内容甚至不再重要了。我会选择 return x?.y?.z?.a?.b?.c?.d||0
.
您当然可以使用保护函数,因为您可能已经注意到阅读您所链接的线程。像 lodash _.get
或者你自己的 guard(a,'b','c','d').
optional chaining browser compatibility
Babel transpiled output of optional chaining
x?.y
将立即 return undefined
如果 x 为空或未定义
浏览器兼容性相对较新。检查 table 兼容性。您应该将 Babel 转译添加到您的管道中。
不带转译的可选链接:
foo = {}
function fn() {
if (foo?.bar?.innerfoo?.innerbar)
return foo.bar.innerfoo.innerbar.x
return 0
}
console.log(fn())
foo = {bar: { innerfoo: { innerbar: { x: 5 }}}}
console.log(fn())
转译代码:
foo = {}
function fn() {
var _foo, _foo$bar, _foo$bar$innerfoo;
if ((_foo = foo) === null || _foo === void 0 ? void 0 : (_foo$bar = _foo.bar) === null || _foo$bar === void 0 ? void 0 : (_foo$bar$innerfoo = _foo$bar.innerfoo) === null || _foo$bar$innerfoo === void 0 ? void 0 : _foo$bar$innerfoo.innerbar) return foo.bar.innerfoo.innerbar.x;
return 0;
}
console.log(fn())
foo = {bar: { innerfoo: { innerbar: { x: 5 }}}}
console.log(fn())