2011-03-18 26 views
2

在C和C++中,我知道在实例化堆栈中的对象与使用'new'在堆上创建它们之间可能存在巨大差异。在Java中,新建和本地之间是否存在性能差异?

这在Java中是一样的吗?

Java中的'new'操作符非常方便(特别是当我不必记住释放/删除用'new'创建的对象时),但这是否意味着我可以与'new'一起狂放?

+6

Java没有基于堆栈的对象。他们都堆在一起。 – skaffman 2011-03-18 14:14:19

+0

我认为你应该小心使用'new',但出于其他原因而不是性能。自行创建依赖关系的类很难进行测试,这通常会导致代码质量低劣。 – 2011-03-18 14:14:36

+0

出于好奇:你将如何实例化Java中的对象而不用新建? – 2011-03-18 14:15:04

回答

5

你不能在堆栈上创建对象,你只能在堆栈上拥有原语和引用,所以这个问题不适用于Java。

已经尝试使用转义分析来优化短暂存在的对象(并且可能将它们放在堆栈上)但是我没有看到任何证据表明这种改进的性能。

在C/C++中会有不同的性能命中/好处的部分原因是Java在堆上有线程本地分配,并且对象不会像循环一样循环使用。 C/C++具有线程本地堆栈,但您需要额外的库以支持多线程对象分配。对象被更加积极地回收,这增加了对象分配的成本。

来自C/C++世界的最大变化之一是发现Java的特性要少得多,但试图使它们充分利用它们(在JVM中有很多复杂的优化)另一方面Java有一个丰富/令人困惑的开放源代码库阵列。

6

呃,在java中没有其他方法来实例化一个对象。

所有对象都使用new创建,并且所有对象都在堆上创建。

在Java中,当你说

MyObject foo; 

你只需声明一个变量(参考)。直到你说

foo = new MyObject(); 

当所有对该对象的引用超出作用域时,该对象变为垃圾收集的可选项。你会注意到在java中没有delete这样的东西:)

6

Java中没有堆栈对象的分配。

只有本地变量(和参数)可以存在于堆栈上,并且只能包含引用或原始值,但不能包含对象。

3
后我

重复:有物体在Java堆栈

在Java中,不像C++,所有的对象都是在堆中分配的,唯一的出路就没有分配时,他们是垃圾回收。

在Java中,与C++不同,变量超出范围并不意味着该对象的析构函数运行;实际上,没有析构函数。所以变量可能会超出范围,但该对象在堆上保持活动状态。

我可以用'新'狂野吗?

是的。首先,因为它是实例化对象的唯一方法。其次,由于JVM非常好,它可以在不到一秒的时间内创建多达2^32个轻量级对象。

+0

Java有一个finalize()方法,它具有与析构函数类似的想法,但不能以相同的方式使用。不确定它可以每秒创建20亿个对象,因为它需要比访问那么多内存更长的时间(即它是一个硬件限制) – 2011-03-18 14:21:43

0

真的没有什么可以在这里比较:你不能在Java堆栈上创建对象。

但是,如果它很舒服,Java 中的基于堆的分配是(至少通常)相当快。 Java的垃圾收集器周期性地“清理”了堆,所以它基本上看起来很像堆栈,并且从中分配很像从堆栈中分配 - 在典型情况下,您有一个指向开始的指针或结束),分配一块内存仅仅意味着添加(或减去)该指针的数量,并返回开始地址(当然,在那里构建一个或多个对象)区域等)

相关问题