閱讀189 返回首頁    go 京東網上商城


Java中的sun.misc.Unsafe包

chronicle項目:https://github.com/peter-lawrey/Java-Chronicle

這個項目是利用mmap機製來實現高效的讀寫數據,號稱每秒寫入5到20百萬條數據。

作者有個測試,寫入1百萬條log用時0.234秒,用java自帶的logger,用時7.347秒。


在看chronicle的源代碼,發現一個牛B的利用Unsafe來直接讀寫內存,從而提高效率的例子。

詳細見這個類:https://github.com/peter-lawrey/Java-Chronicle/blob/master/src/main/java/vanilla/java/chronicle/impl/UnsafeExcerpt.java


Unsafe包的參考:https://www.docjar.com/docs/api/sun/misc/Unsafe.html

下麵這個例子演示了簡單的修改一個byte[]的數據。

這個例子在eclipse裏不能直接編譯,要到項目的屬性,Java Compiler,Errors/Warnings中Forbidden reference(access rules)中設置為warning。

另外,因為sun.misc.Unsafe包不能直接使用,所有代碼裏用反射的技巧得到了一個Unsafe的實例。

import java.lang.reflect.Field;
import java.util.Arrays;
import sun.misc.Unsafe;

public class Test {
	private static int byteArrayBaseOffset;

	public static void main(String[] args) throws SecurityException,
			NoSuchFieldException, IllegalArgumentException,
			IllegalAccessException {
		Field theUnsafe = Unsafe.class.getDeclaredField("theUnsafe");
		theUnsafe.setAccessible(true);
		Unsafe UNSAFE = (Unsafe) theUnsafe.get(null);
		System.out.println(UNSAFE);

		byte[] data = new byte[10];
		System.out.println(Arrays.toString(data));
		byteArrayBaseOffset = UNSAFE.arrayBaseOffset(byte[].class);

		System.out.println(byteArrayBaseOffset);
		UNSAFE.putByte(data, byteArrayBaseOffset, (byte) 1);
		UNSAFE.putByte(data, byteArrayBaseOffset + 5, (byte) 5);
		System.out.println(Arrays.toString(data));
	}
}


最後更新:2017-04-02 16:47:36

  上一篇:go Android TransitionDrawable&StateListDrawable的使用
  下一篇:go Android Activity切換動畫效果的修改