在Java 8中,为什么ArrayList的默认容量现在为零? - java

我记得,在Java 8之前,ArrayList的默认容量为10。

出乎意料的是,对默认(无效)构造函数的评论仍然显示:Constructs an empty list with an initial capacity of ten.

来自ArrayList.java

/**
 * Shared empty array instance used for default sized empty instances. We
 * distinguish this from EMPTY_ELEMENTDATA to know how much to inflate when
 * first element is added.
 */
private static final Object[] DEFAULTCAPACITY_EMPTY_ELEMENTDATA = {};

...

/**
 * Constructs an empty list with an initial capacity of ten.
 */
public ArrayList() {
    this.elementData = DEFAULTCAPACITY_EMPTY_ELEMENTDATA;
}

参考方案

从技术上讲,如果您允许对备用数组进行延迟初始化,则它为10,而不是零。看到:

public boolean add(E e) {
    ensureCapacityInternal(size + 1);
    elementData[size++] = e;
    return true;
}

private void ensureCapacityInternal(int minCapacity) {
    if (elementData == DEFAULTCAPACITY_EMPTY_ELEMENTDATA) {
        minCapacity = Math.max(DEFAULT_CAPACITY, minCapacity);
    }

    ensureExplicitCapacity(minCapacity);
}

哪里

/**
 * Default initial capacity.
 */
private static final int DEFAULT_CAPACITY = 10;

您所指的只是大小为零的初始数组对象,该对象在所有最初为空的ArrayList对象之间共享。即懒惰地保证了10的容量,Java 7中也存在这种优化。

诚然,建设者合同并不完全准确。也许这是造成混乱的根源。

背景

这是Mike Duigou的电子邮件

我已经发布了空ArrayList和HashMap补丁的更新版本。

http://cr.openjdk.java.net/~mduigou/JDK-7143928/1/webrev/

修订后的实现对这两个类都没有引入新的字段。对于ArrayList,仅当以默认大小创建列表时,才会对后备数组进行延迟分配。根据我们的性能分析团队的说法,大约有85%的ArrayList实例是在默认大小下创建的,因此此优化将在绝大多数情况下有效。

对于HashMap,创意使用阈值字段来跟踪请求的初始大小,直到需要存储桶数组为止。在读取方面,使用isEmpty()测试空映射案例。在写入大小上,比较(table == EMPTY_TABLE)用于检测是否需要对存储桶数组进行充气。在readObject中,还有更多工作来尝试选择有效的初始容量。

发件人:http://mail.openjdk.java.net/pipermail/core-libs-dev/2013-April/015585.html

在Java 8流中,如何过滤掉不是枚举有效值的字符串? - java

我有一个枚举,我称之为对我的应用程序重要的安全权限的Permission。在数据库中,用户可能具有与我的应用程序无关的其他权限。从数据库中读取用户时,我得到一个List<String>,并且我想建立一个List<Permission>,而忽略了那些不是枚举值的字符串。public enum Permission { ADMIN, US…

JAVA 8具有任何匹配属性的对象的过滤器列表 - java

我的要求是通过匹配任何属性的字符串来过滤对象列表。例如,假设Contact类具有三个属性:街道,城市,电话。我知道java流过滤器是如何工作的,在这里我必须将输入字符串与每个属性进行比较,如下所示:contactList.stream().filter(contact -> contact.getStreet().equals("dubai&…

JAVA:字节码和二进制有什么区别? - java

java字节代码(已编译的语言,也称为目标代码)与机器代码(当前计算机的本机代码)之间有什么区别?我读过一些书,他们将字节码称为二进制指令,但我不知道为什么。 参考方案 字节码是独立于平台的,在Windows中运行的编译器编译的字节码仍将在linux / unix / mac中运行。机器代码是特定于平台的,如果在Windows x86中编译,则它将仅在Win…

java:继承 - java

有哪些替代继承的方法? java大神给出的解决方案 有效的Java:偏重于继承而不是继承。 (这实际上也来自“四人帮”)。他提出的理由是,如果扩展类未明确设计为继承,则继承会引起很多不正常的副作用。例如,对super.someMethod()的任何调用都可以引导您通过未知代码的意外路径。取而代之的是,持有对本来应该扩展的类的引用,然后委托给它。这是与Eric…

Java:BigInteger,如何通过OutputStream编写它 - java

我想将BigInteger写入文件。做这个的最好方式是什么。当然,我想从输入流中读取(使用程序,而不是人工)。我必须使用ObjectOutputStream还是有更好的方法?目的是使用尽可能少的字节。谢谢马丁 参考方案 Java序列化(ObjectOutputStream / ObjectInputStream)是将对象序列化为八位字节序列的一种通用方法。但…