提交 5a56777c authored 作者: Thomas Mueller's avatar Thomas Mueller

Undo changes

上级 d4f22985
...@@ -5,7 +5,6 @@ ...@@ -5,7 +5,6 @@
* Initial Developer: H2 Group * Initial Developer: H2 Group
*/ */
package org.h2.util; package org.h2.util;
import java.util.Arrays;
/** /**
* A list of bits. * A list of bits.
...@@ -160,13 +159,11 @@ public class BitField { ...@@ -160,13 +159,11 @@ public class BitField {
data[addr] &= ~getBitMask(i); data[addr] &= ~getBitMask(i);
} }
// this is static to encourage compiler to inline it private int getAddress(int i) {
private static int getAddress(int i) {
return i >> ADDRESS_BITS; return i >> ADDRESS_BITS;
} }
// this is static to encourage compiler to inline it private long getBitMask(int i) {
private static long getBitMask(int i) {
return 1L << (i & ADDRESS_MASK); return 1L << (i & ADDRESS_MASK);
} }
...@@ -188,50 +185,24 @@ public class BitField { ...@@ -188,50 +185,24 @@ public class BitField {
/** /**
* Enable or disable a number of bits. * Enable or disable a number of bits.
* *
* @author Samuel Van Oort
* @param start the index of the first bit to enable or disable * @param start the index of the first bit to enable or disable
* @param len the number of bits to enable or disable * @param len the number of bits to enable or disable
* @param value the new value * @param value the new value
*/ */
public void setRange(int start, int len, boolean value) { public void setRange(int start, int len, boolean value) {
int startIdx = getAddress(start); // go backwards so that OutOfMemory happens
int endIdx = getAddress(start + len - 1); // before some bytes are modified
int end = start+len; for (int i = start + len - 1; i >= start; i--) {
set(i, value);
// expand BitField if writing past end, unless clearing
// this prevents OutOfMemoryError mid-modify
int datalen = data.length;
if (endIdx >= datalen) {
if (!value && startIdx >= datalen) {
// trying to clear past end of set bits - nothing to do
return;
}
expandCapacity(endIdx);
}
long startMask = (~0L) << start;
long endMask = (~0L) >>> -end;
// if operating on one long, mask is combined
if (startIdx == endIdx) {
startMask &= endMask;
} }
// set first long element in range
if (value) {
data[startIdx] |= startMask;
} else {
data[startIdx] &= ~startMask;
} }
// work on additional elements only if needed private void set(int i, boolean value) {
if (startIdx != endIdx) {
// set the last long element in range
if (value) { if (value) {
data[endIdx] |= endMask; set(i);
} else { } else {
data[endIdx] &= ~endMask; clear(i);
}
// set longs fully in the range very quickly to all 1 or all 0
Arrays.fill(data, startIdx + 1, endIdx, value ? -1L : 0L);
} }
} }
} }
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论