为什么不与QUOT声明的变量;尽量"在&QUOT范围;抓"或QUOT;最后"? [英] Why aren't variables declared in "try" in scope in "catch" or "finally"?

查看:118
本文介绍了为什么不与QUOT声明的变量;尽量"在&QUOT范围;抓"或QUOT;最后"?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在C#和Java中(也可能是其他语言),在一个尝试块声明的变量不在范围在相应的捕捉或最后块。例如,下面的code不能编译:

  {尝试
  字符串s =测试;
  //(更多code ...)
}
抓{
  Console.Out.WriteLine(多个); // Java的球迷:想的System.out.println,而不是在这里
}

在此code,在catch块参考送发生编译时错误,因为s是仅在try块范围。 (在Java中,编译错误是S解决不了;在C#中,它的名称's'不在目前情况下存在)

这个问题一般的解决方法似乎是刚刚在try块之前,而不是声明变量,而不是内部的try块:

 的String;
尝试{
  S =测试;
  //(更多code ...)
}
抓{
  Console.Out.WriteLine(多个); // Java的球迷:想的System.out.println,而不是在这里
}

不过,至少对我来说,(1)这种感觉就像一个笨重的解决方案,以及(2)它在结果中具有比预期的程序员一个更大的范围(该方法的整个剩余的变量,而不是只上下文在try-catch-最后)。

我的问题是,是什么/是这种语言的设计决策背后的理由(S)(在Java中,在C#中,和/或任何其他适用的语言)?


解决方案

两件事情:


  1. 一般情况下,JavaScript有只2级范围:全球性和功能。但是,try / catch语句是个例外(无punn意)。当一个异常被抛出,异常对象获取分配给它的变量,该变量的对象仅仅是抓一节中提供,并尽快追赶完成销毁。


  2. (更重要的)。你可以不知道在try块抛出异常。它可能已被宣告您的变量之前。因此,这是很难说的变量会是怎样适用于捕捉/ finally子句。考虑下面的情况下,如果作用域是如你所说:


 

 
    尝试
    {
        抛出新的ArgumentException(一些操作抛出异常);
        字符串s =嗒嗒;
    }
    赶上(E上的ArgumentException)
    {
        Console.Out.WriteLine(多个);
    }
 

这显然是一个问题 - 当你到达了异常处理程序,S不会被宣布。由于捕捞量是为了处理特殊情况下finallys的必须的执行,是安全的,这宣告在编译时有问题远比在运行时更好。

In C# and in Java (and possibly other languages as well), variables declared in a "try" block are not in scope in the corresponding "catch" or "finally" blocks. For example, the following code does not compile:

try {
  String s = "test";
  // (more code...)
}
catch {
  Console.Out.WriteLine(s);  //Java fans: think "System.out.println" here instead
}

In this code, a compile-time error occurs on the reference to s in the catch block, because s is only in scope in the try block. (In Java, the compile error is "s cannot be resolved"; in C#, it's "The name 's' does not exist in the current context".)

The general solution to this issue seems to be to instead declare variables just before the try block, instead of within the try block:

String s;
try {
  s = "test";
  // (more code...)
}
catch {
  Console.Out.WriteLine(s);  //Java fans: think "System.out.println" here instead
}

However, at least to me, (1) this feels like a clunky solution, and (2) it results in the variables having a larger scope than the programmer intended (the entire remainder of the method, instead of only in the context of the try-catch-finally).

My question is, what were/are the rationale(s) behind this language design decision (in Java, in C#, and/or in any other applicable languages)?

解决方案

Two things:

  1. Generally, JavaScript has just 2 levels of scope: global and function. But, try/catch is an exception (no punn intended). When an exception is thrown and the exception object gets a variable assigned to it, that object variable is only available within the "catch" section and is destroyed as soon as the catch completes.

  2. (and more importantly). You can't know where in the try block the exception was thrown. It may have been before your variable was declared. Therefore it is impossible to say what variables will be available for the catch/finally clause. Consider the following case, where scoping is as you suggested:


    try
    {
        throw new ArgumentException("some operation that throws an exception");
        string s = "blah";
    }
    catch (e as ArgumentException)
    {  
        Console.Out.WriteLine(s);
    }
 

This clearly is a problem - when you reach the exception handler, s will not have been declared. Given that catches are meant to handle exceptional circumstances and finallys must execute, being safe and declaring this a problem at compile time is far better than at runtime.

这篇关于为什么不与QUOT声明的变量;尽量"在&QUOT范围;抓"或QUOT;最后"?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
相关文章
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆