循环中的局部变量声明

时间:2017-03-07 11:13:28

标签: java class core

当我运行以下代码时,它给出了编译时错误。

public class Test {
    public static void main(String[] args) {
        for (int i = 0; i < 100; i++)
       Test2 obj = new Test2();// Compile time error- Multiple markers at this line
        System.out.println(Test2.numCreated());
    }
}

class Test2 {
    private static long number= 0;


    public static long numCreated() {
        return number;
    }
}

但是当我将局部变量声明语句Test2 obj= new Test2()直接放在一个块中时,每个东西都能正常工作。

有人可以解释一下这背后的原因或为什么Java开发人员这样做了吗?

4 个答案:

答案 0 :(得分:6)

编译器非常聪明,如果你省略 {} 那么 obj 对象没有理由被声明,因为它立即超出了范围

记得省略 {} 表示只有下一行属于for范围...

你的意思是肯定的:

for (int i = 0; i < 100; i++){
      Test2 obj = new Test2();
}

但范围是什么? here more info

scope是一个对象可见的封闭区域,在这种情况下,对象 obj 在for循环中声明,这意味着你只能在循环中使用它并且它将准备就绪循环完成后立即成为GC ...

答案 1 :(得分:1)

正如上面的回答所说,你得到了错过for循环 {} 的支持

注意:如果删除大括号,它只会读取第一行指令。不会读取任何其他行。如果要执行的指令行超过1行,请使用大括号 - 否则将抛出异常。

答案 2 :(得分:0)

如果你没有把括号 {} ,那么循环只会执行一个语句。由于您在该特定行中声明了obj,因此之后无法使用它。所以编译器会事先警告你。

如果要执行多个语句并使用变量,则必须使用 {}

for (int i = 0; i < 100; i++){
       Test2 obj = new Test2();
       System.out.println(Test2.numCreated());
}

现在它将正常工作,因为两个语句都属于循环并且在循环的范围内。循环执行完毕后,obj将被垃圾收集。

答案 3 :(得分:0)

请注意,这不仅限于Where(x => !x.GetProperty<String>("myCategory").Contains(myString)) 循环。问题实际上是您的示例中的语句是“本地变量声明声明”(jls-14.4),特别是规范中的以下行:

  

每个局部变量声明语句都会立即被一个块包含。

您的示例可以缩减为

 @Before("execution(* com.dummy.pkg..*.*(..))")
    public Response<Object> beforeServiceAspect(JoinPoint joinPoint) throws Exception {

            Object[] signatureArgs = joinPoint.getArgs();

           String sessionId=(String) signatureArgs[0];


         if(null==sessionId||sessionId.isEmpty()||!loginService.getUserInfo(sessionId))
           {
                Response.setStatusCode("401");
                Response.setC
                Response.setResultString("Unauthorized User");
                  return  Response;    
 //this is where i  want to  return in case of program enter here   
//**point 1** 
           }
   //**point 2**  where execution reaches then resume normal flow 
return "";
}

也无法编译。

只要添加一个块,它就可以很好地编译:

for