1 30 31 32 package org.hsqldb.persist; 33 34 import org.hsqldb.lib.DoubleIntIndex; 35 36 43 public class DataFileBlockManager { 44 45 private DoubleIntIndex lookup; 46 private final int capacity; 47 private int midSize; 48 private final int scale; 49 private long releaseCount; 50 private long requestCount; 51 private long requestSize; 52 53 long lostFreeBlockSize; 55 boolean isModified; 56 57 60 public DataFileBlockManager(int capacity, int scale, long lostSize) { 61 62 lookup = new DoubleIntIndex(capacity, true); 63 64 lookup.setValuesSearchTarget(); 65 66 this.capacity = capacity; 67 this.scale = scale; 68 this.lostFreeBlockSize = lostSize; 69 this.midSize = 128; } 71 72 74 void add(int pos, int rowSize) { 75 76 isModified = true; 77 78 if (capacity == 0) { 79 lostFreeBlockSize += rowSize; 80 81 return; 82 } 83 84 releaseCount++; 85 86 if (lookup.size() == capacity) { 88 resetList(); 89 } 90 91 lookup.add(pos, rowSize); 92 } 93 94 97 int get(int rowSize) { 98 99 if (lookup.size() == 0) { 100 return -1; 101 } 102 103 int index = lookup.findFirstGreaterEqualKeyIndex(rowSize); 104 105 if (index == -1) { 106 return -1; 107 } 108 109 requestCount++; 111 112 requestSize += rowSize; 113 114 int length = lookup.getValue(index); 115 int difference = length - rowSize; 116 int key = lookup.getKey(index); 117 118 lookup.remove(index); 119 120 if (difference >= midSize) { 121 int pos = key + (rowSize / scale); 122 123 lookup.add(pos, difference); 124 } else { 125 lostFreeBlockSize += difference; 126 } 127 128 return key; 129 } 130 131 int size() { 132 return lookup.size(); 133 } 134 135 long getLostBlocksSize() { 136 return lostFreeBlockSize; 137 } 138 139 boolean isModified() { 140 return isModified; 141 } 142 143 void clear() { 144 removeBlocks(lookup.size()); 145 } 146 147 private void resetList() { 148 149 if (requestCount != 0) { 150 midSize = (int) (requestSize / requestCount); 151 } 152 153 int first = lookup.findFirstGreaterEqualSlotIndex(midSize); 154 155 if (first < lookup.size() / 4) { 156 first = lookup.size() / 4; 157 } 158 159 removeBlocks(first); 160 } 161 162 private void removeBlocks(int blocks) { 163 164 for (int i = 0; i < blocks; i++) { 165 lostFreeBlockSize += lookup.getValue(i); 166 } 167 168 lookup.removeRange(0, blocks); 169 } 170 171 private void checkIntegrity() throws NullPointerException {} 172 } 173 | Popular Tags |