克隆一个int [] - 有人得到了更快的建议吗?

时间:2011-05-27 00:14:40

标签: java arrays performance

我正盯着一个配置文件,其中一个CPU热点是一个包含克隆最终静态int []的函数。你可能会问,'为什么?'调用者使用结果作为散列过程的起点。

换句话说,代码需要(逻辑上):

  1. 制作新阵列
  2. 获取散列种子(与数组大小一样多)
  3. 将值放在从散列种子计算的新数组中。这是一个迭代 算法,所以让种子从数组开始是有利的 - 因此从种子数组的克隆开始的想法。
  4. 在我放弃或开始使用微基准测试之前,我发布了这个问题,以防任何人对使用clone()与Arrays.copyOf以及新的和arraycopy的内幕有什么特别的了解。

4 个答案:

答案 0 :(得分:5)

Arrays.copyOf充分利用了记忆,就像引擎盖下的说明一样。此外,索引越界检查越少。如果您逐个指定值,则每次都会进行“绑定”检查。

我没有针对每个建议的选项进行基准测试,但我确信Arrays.copyOf()会比new int[] + for(...)更快。

另一方面,我不确定Arrays.copyOf()是否比int[] myCopy = myOrig.clone()更有效,因为克隆发生在基本类型数组上。编译器很有可能生成优化的字节码。只有测试才能提供明确的答案。

答案 1 :(得分:3)

Arrays.copyOf使用System.arraycopy但首先添加了一些边界检查

public static int[] copyOf(int[] original,
    int newLength) 
{
        if (0 < = newLength) {
            return copyOfRange(original, 0, newLength);
        }
        throw new NegativeArraySizeException();
}


public static int[] copyOfRange(int[] original,
    int start,
    int end) 
{
        if (start < = end) {
            if (original.length  >= start && 0 < = start) {
                int length = end - start;
                int copyLength = Math.min(length, original.length - start);
                int[] copy = new int[length];
                System.arraycopy(original, start, copy, 0, copyLength);
                return copy;
            }
            throw new ArrayIndexOutOfBoundsException();
        }
        throw new IllegalArgumentException();
}

我是从http://www.docjar.com/docs/api/java/util/Arrays.html得到的,所以使用它可能略微Arrays.copyOf

更好
int[] newone = new int[orig.length];
System.arraycopy(orig, 0, newone , 0, orig.length);

但实际上最好保留数组并在完成后重复使用它们

答案 2 :(得分:0)

如果代码属于您,请执行以下操作:

public final class ReadOnlyIntArray {
  private final int[] _contents;

  public ReadOnlyIntArray(int[] data) {
    _contents = (int[]) data.clone();
  }

  public int get(int index) {
    return _contents[index];
  }
}

final static内容保留在其中一个内容中,并返回此对象而不是int[]。如果他们做任何破坏性的事情,强迫消费者克隆。

我经常觉得这个构造应该是java.lang中的核心构造之一,它允许返回Class[]Method[]等的代码不必每次都克隆

答案 3 :(得分:0)

在基本类型数组上使用clone()比使用Java 1.6 / 1.7 x86客户端虚拟机的new []System.arraycopy组合慢约50%,但速度与x64服务器VM。

对于1000个或更少元素的数组大小,复制不是操作中最昂贵的部分,而是数组本身的创建(即创建2048个元素的字节数组需要3倍于将2048个元素复制到System.arraycopy)。如果你回收临时阵列,你可以获得一些改进。