[英]Why does StringBuffer/StringBuilder not override equals or hashCode?
[英]Why StringBuilder does not print?
为什么StringBuilder不会在小代码中打印它应该打印的内容
public final class Test1 {
public void test() {
System.out.println(setFin().toString());
}
protected StringBuilder setFin() {
StringBuilder builder = new StringBuilder();
try {
builder.append("John");
return builder.append("Ibrahim");
} finally {
System.out.println("In finaly"); // builder.append("-DarElBeida");
builder = null;
}
}
public static void main(String args[]){
new Test1().test();
}
}
在setFin()
执行的最后一个语句(在finally
块中)我已经为builder
分配了null
,但是我的代码打印"In finally"
,然后是"JohnIbrahim"
。 任何人都可以向我解释这里发生了什么吗?
当try
块内有return
语句时,它将在实际返回之前执行finally
块。
并且该方法不返回null
因为return
语句包含对实际StringBuilder对象的引用,而不是对变量builder
的引用。
设置builder == null
不会删除StringBuilder本身,它只是删除了builder
对它的引用。
这种行为可能令人困惑。 为了清楚起见,从try / catch / finally块外部返回可能会有所帮助:
StringBuilder builder = new StringBuilder();
try {
builder.append("John");
builder.append("Ibrahim");
} finally {
System.out.println("In finaly"); // builder.append("-DarElBeida");
builder = null;
}
return builder;
你正在回归builder
。 之后,将builder
设置为null。 但它已经归还了。 之后你对变量做了什么并不重要。 返回值已经“锁定”。 你能做的就是弄乱正在返回的对象。 例如, builder.setLength(0)
将删除所有文本。
从理论上讲,您也可以从finally块return null
,但强烈建议不要(更改返回值)。
在finally
块运行之前,将评估返回值并将其存储在堆栈中 。 请注意,堆栈上的值实际上是StringBuilder
引用的值。 因此,即使您将builder
设置为null
,也不会更改堆栈上已有的计算return
值。 但是,如果返回值是对可变对象的引用,则可以改变对象,并且更改将在return
值中可见。
例如,如果在finally
块中添加以下语句而不是nullifying
引用nullifying
:
builder.append("Hrithik Roshan");
然后你会在返回值中看到该内容。
但是,如果再次从finally
块return
builder
,它将覆盖先前计算的return
语句。 但请注意,这不是一个好主意。
finally
总是执行,除非JVM在try
块完成之前崩溃或退出。
如果try
块由于return
语句而完成,则在finally
块执行之前 ,将return
的表达式计算为单个值。 该值被保存,并在finally
块完成时返回。
因此, builder = null
的赋值没有任何效果,因为builder.append("Ibrahim")
的评估已经在finally
执行时完成。
builder
包含对您创建的StringBuilder的引用。 当您执行builder = null
,您将builder
设置为不再保留该引用。 StringBuilder本身仍然存在(至少在垃圾收集发生之前)。
发生的事情是你的return
语句返回对StringBuilder的引用。 它没有返回变量builder
; 它返回对builder
引用的东西的引用。 因此,即使您正在消除变量,return语句也已经引用了创建的对象。
如果在finally
块中打印了builder
,那么它将为null。
第一个执行的return
语句,它执行返回StringBuilder
引用的builder.append("Ibrahim")
。 引用被保存到堆栈中。 然后执行了finally
阻止。 您已经取消了局部变量,但在方法实际返回后, StringBuilder
对象的引用传递给调用者。 这就是打印所有值的原因。 错误是您为finally
块中的builder
分配了一个从未使用过的值。 堆栈在实际返回之前保持return
语句操作数的值,即在finally
块之后。 如果您不想从方法返回引用,则应在finally
块中return null
,这将覆盖堆栈中的值。
} finally {
System.out.println("In finaly"); // builder.append("-DarElBeida");
return null;
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.