- iOS/Objective-C 元类和类别
- objective-c - -1001 错误,当 NSURLSession 通过 httpproxy 和/etc/hosts
- java - 使用网络类获取 url 地址
- ios - 推送通知中不播放声音
尽管广泛阅读了 JDK 源代码并检查了内在例程,但我还是无法完全理解这个结果。
我正在测试清除 ByteBuffer
,使用 ByteBuffer.putLong(int index, long value)
通过 allocateDirect
分配。基于 JDK 代码,如果缓冲区处于“ native 字节顺序”,这将导致单个 8 字节写入,或者字节交换,如果不是,则后跟相同。
所以我希望 native 字节顺序(对我来说是小端)至少与非 native 一样快。然而,事实证明,非本地人的速度快了约 2 倍。
这是我在 Caliper 0.5x 中的基准测试:
...
public class ByteBufferBench extends SimpleBenchmark {
private static final int SIZE = 2048;
enum Endian {
DEFAULT,
SMALL,
BIG
}
@Param Endian endian;
private ByteBuffer bufferMember;
@Override
protected void setUp() throws Exception {
super.setUp();
bufferMember = ByteBuffer.allocateDirect(SIZE);
bufferMember.order(endian == Endian.DEFAULT ? bufferMember.order() :
(endian == Endian.SMALL ? ByteOrder.LITTLE_ENDIAN : ByteOrder.BIG_ENDIAN));
}
public int timeClearLong(int reps) {
ByteBuffer buffer = bufferMember;
while (reps-- > 0) {
for (int i=0; i < SIZE / LONG_BYTES; i+= LONG_BYTES) {
buffer.putLong(i, reps);
}
}
return 0;
}
public static void main(String[] args) {
Runner.main(ByteBufferBench.class,args);
}
}
结果是:
benchmark type endian ns linear runtime
ClearLong DIRECT DEFAULT 64.8 =
ClearLong DIRECT SMALL 118.6 ==
ClearLong DIRECT BIG 64.8 =
这是一致的。如果我将 putLong
换成 putFloat
,它的原生顺序大约快 4 倍。如果你看看 putLong
是如何工作的,它在非本地情况下做的工作绝对更多:
private ByteBuffer putLong(long a, long x) {
if (unaligned) {
long y = (x);
unsafe.putLong(a, (nativeByteOrder ? y : Bits.swap(y)));
} else {
Bits.putLong(a, x, bigEndian);
}
return this;
}
请注意,unaligned
在任何一种情况下都是正确的。 native 和非 native 字节顺序之间的唯一区别是 Bits.swap
,它有利于 native 大小写(小端)。
最佳答案
总结机械同情邮件列表中的讨论:
1.OP 描述的异常在我的设置 (JDK7u40/Ubuntu13.04/i7) 上无法重现,导致在所有情况下堆和直接缓冲区的性能一致,直接缓冲区提供巨大的性能优势:
BYTE_ARRAY DEFAULT 211.1 ==============================
BYTE_ARRAY SMALL 199.8 ============================
BYTE_ARRAY BIG 210.5 =============================
DIRECT DEFAULT 33.8 ====
DIRECT SMALL 33.5 ====
DIRECT BIG 33.7 ====
Bits.swap(y) 方法被内在化为一条指令,因此不能/不应该真正解释很多差异/开销。
2.上述结果(即与 OP 经验相矛盾)由另一位参与者编写的 naive hand rolled benchmark 和 JMH benchmark 独立确认。
这让我相信您遇到了一些本地问题或某种基准测试框架问题。如果其他人可以运行该实验并查看他们是否可以重现您的结果,那将很有值(value)。
关于java - ByteBuffer.putLong 使用非原生 ByteOrder 快 2 倍,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19265835/
我需要从 mysql 数据库访问 php 数据,该数据库的内容由 java 应用程序设置,以便计算正确的用户哈希值。 我似乎无法使用 php 复制代码,我认为我的问题在于 PHP 无法处理据我所知的
本文整理了Java中com.yahoo.memory.WritableMemory.putLong()方法的一些代码示例,展示了WritableMemory.putLong()的具体用法。这些代码示例
Unsafe.putAddress(long address, long x) 之间有什么区别?方法和Unsafe.putLong(long address, long x)方法? 最佳答案 Java
我有一个长。我知道这个 long 不是很大。实际上,它可以被编码为 7 个字节的无符号整数。 我想使用 ByteBuffer 和 little endian 将我的 long 写入 byte[7]。
尽管广泛阅读了 JDK 源代码并检查了内在例程,但我还是无法完全理解这个结果。 我正在测试清除 ByteBuffer,使用 ByteBuffer.putLong(int index, long val
当我尝试使用 FirestoreRecyclerAdapter 从 Firestore 检索数据时,它没有显示。 错误日志 Accessing hidden method Lsun/misc/Unsa
我是一名优秀的程序员,十分优秀!