抛出字符串而不是错误

bil*_*.cn 64 javascript

既然我们可以throw在Javascript中使用关键字抛出任何内容,那么我们不能直接抛出错误消息字符串吗?

有谁知道这有什么捕获?

让我为此添加一些背景:很多时候,在JavaScript世界中,人们依赖于参数检查而不是使用try-catch机制,所以只抛出致命错误才有意义throw.仍然,为了能够捕获一些系统错误,我必须为我自己的错误使用不同的类,而不是创建Error的子类,我想我应该只使用String.

lan*_*nzz 44

抛出你喜欢的东西是可以的,但请记住,如果catch不在你自己的代码之外,那么它可能需要一个完整的Error实例而不是一个普通的字符串.

  • 例如,它可能假设[`Error`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Error)的`.message`属性是一个字符串,尝试在其上调用一个字符串方法,然后爆炸. (5认同)
  • 你*可以*,但我不会说它是"好的"*. (4认同)
  • @BenjaminGruenbaum 如果你在 Chrome 中抛出一个字符串,你确实会得到一个堆栈跟踪。例如 ` function a() { throw "Hello World"; } a();` 将有一个像这样的堆栈跟踪: `a @ main.js:4 (anonymous) @ main.js:7` (4认同)
  • 这是一个可怕的主意,因为这意味着您将需要更多的时间来调试没有堆栈跟踪的错误。 (2认同)

Ber*_*rgi 38

是的,您可以抛出其他值,但这不是一个好习惯.

有谁知道这有什么捕获?

字符串不是错误对象,并且不传达任何有用的调试信息.Devtools依赖于此,例如创建错误的文件和行,throw位置处的堆栈跟踪等,它们可用作Error对象的属性.

每当你想到抛出一个原始字符串值时,抛出一个new Error("<the string>")代替.

  • 值得注意的是,即使你扔了一个字符串,Chrome devtools也会打印堆栈跟踪.你失去了`.stack`属性,这对于一些自动错误处理很有用(例如,当设置自动报告错误到服务器以便你调试生产中出错的东西时),但这更像是一个边缘情况; 如果你抛出字符串,浏览器中的日常手动调试工作正常. (8认同)
  • 另请注意,抛出(和捕获)字符串而不是错误具有速度优势:https://jsbench.me/1gkqk6dm06/2 我的结果:错误为 237k ops/s,字符串为 1.168m ops/s。这几乎不重要,但理论上可以。(例如,如果您出于某种原因使用字符串抛出只是为了“转义”到更高级别的函数调用) (2认同)

Max*_*Art 16

你知道,你可以在邮件中抛出错误.

try {
    throw new Error("This is an error");
} catch (e) {
    alert(e.message); // This is an error
}
Run Code Online (Sandbox Code Playgroud)

但你实际上可以抛出字符串:

try {
    throw "This is an error";
} catch (e) {
    alert(e); // This is an error
}
Run Code Online (Sandbox Code Playgroud)

  • 很抱歉没有提出问题.我知道这些都有效,但我对直接使用Strings而不是使用Error对象的潜在问题感兴趣. (3认同)

Tim*_*inn 5

正如其他人在上面提到的,如果你没有抛出一个 Error 对象,那么你必须有 try/catch 块来捕获这些对象并适当地处理它们,否则调试就会受到伤害。

然而,当为了控制程序流等非错误处理目的而抛出错误时,这可能是一种throw没有错误的有用方法。

当使用 throws 来控制程序流时,它在任何语言中都可能是低效的,因为运行时通常会做很多繁重的工作来展开调用堆栈信息并序列化数据,使其可用于用户范围。通过避免错误创建,您可以避免这种性能下降。关键是您必须在调用堆栈上有一个知道如何处理这种情况的处理程序。例如,如果您throw {isHardStop: true, stopCode: SOME_CODE}设计处理程序来检测这一点,您可能能够扁平化一些代码或选择更简洁的语法。

这个梯子案例的处理程序的结构可以是这样的:

try { ... } catch(thr) {
    if(!thr){
       // Is not Error or Json - Handle accordingly
    } else if(thr.isHardStop){
       // Handle the stop
    } else {
       // Most likely a real error. Handle accordingly
    }
}
Run Code Online (Sandbox Code Playgroud)