use of org.apache.ignite.internal.processors.cache.persistence.tree.io.BPlusIO in project ignite by apache.
the class CompressionProcessorTest method doTestBTreePage.
/**
* @param io Page IO.
* @throws IgniteCheckedException If failed.
*/
private void doTestBTreePage(BPlusIO<byte[]> io) throws IgniteCheckedException {
Random rnd = ThreadLocalRandom.current();
final byte[][] rows = new byte[3][io.getItemSize()];
for (int i = 0; i < rows.length; i++) rnd.nextBytes(rows[i]);
ByteBuffer page = allocateDirectBuffer(pageSize);
long pageAddr = bufferAddress(page);
long pageId = PageIdUtils.pageId(PageIdAllocator.INDEX_PARTITION, PageIdAllocator.FLAG_IDX, 171717);
io.initNewPage(pageAddr, pageId, pageSize, null);
checkIo(io, page);
Function<ByteBuffer, List<?>> getContents = (buf) -> {
long addr = bufferAddress(buf);
int cnt = io.getCount(addr);
List<Object> list = new ArrayList<>(cnt);
for (int i = 0; i < cnt; i++) {
if (!io.isLeaf())
list.add(((BPlusInnerIO) io).getLeft(addr, i));
try {
list.add(new Bytes(io.getLookupRow(null, addr, i)));
} catch (IgniteCheckedException e) {
throw new IllegalStateException(e);
}
if (!io.isLeaf())
list.add(((BPlusInnerIO) io).getRight(addr, i));
}
return list;
};
// Empty page.
checkCompressDecompress(page, getContents, false);
int cnt = io.getMaxCount(pageAddr, pageSize);
for (int i = 0; i < cnt; i++) {
byte[] row = rows[rnd.nextInt(rows.length)];
io.insert(pageAddr, i, row, row, 777_000 + i, false);
}
if (io.isLeaf())
// Page must be full.
assertEquals(pageSize, io.getItemsEnd(pageAddr));
// Full page.
checkCompressDecompress(page, getContents, io.isLeaf());
io.setCount(pageAddr, cnt / 2);
// Half page.
checkCompressDecompress(page, getContents, false);
}
use of org.apache.ignite.internal.processors.cache.persistence.tree.io.BPlusIO in project ignite by apache.
the class IgniteIndexReader method horizontalTreeScan.
/**
* Traverse single index tree by each level horizontally.
*
* @param rootPageId Root page id.
* @param treeName Tree name.
* @param itemStorage Items storage.
* @return Tree traversal info.
*/
private TreeTraversalInfo horizontalTreeScan(long rootPageId, String treeName, ItemStorage itemStorage) {
FilePageStore store = filePageStore(partId(rootPageId));
Map<Long, List<Throwable>> errors = new HashMap<>();
Map<Class, Long> ioStat = new HashMap<>();
TreeTraverseContext treeCtx = new TreeTraverseContext(treeName, store, ioStat, errors, null, null, null);
ByteBuffer buf = allocateBuffer(pageSize);
try {
long addr = bufferAddress(buf);
readPage(store, rootPageId, buf);
PageIO pageIO = PageIO.getPageIO(addr);
if (!(pageIO instanceof BPlusMetaIO))
throw new IgniteException("Root page is not meta, pageId=" + rootPageId);
BPlusMetaIO metaIO = (BPlusMetaIO) pageIO;
ioStat.compute(metaIO.getClass(), (k, v) -> v == null ? 1 : v + 1);
int lvlsCnt = metaIO.getLevelsCount(addr);
long[] firstPageIds = IntStream.range(0, lvlsCnt).mapToLong(i -> metaIO.getFirstPageId(addr, i)).toArray();
for (int i = 0; i < lvlsCnt; i++) {
long pageId = firstPageIds[i];
while (pageId > 0) {
try {
buf.rewind();
readPage(store, pageId, buf);
pageIO = PageIO.getPageIO(addr);
if (i == 0 && !(pageIO instanceof BPlusLeafIO))
throw new IgniteException("Not-leaf page found on leaf level, pageId=" + pageId + ", level=" + i);
if (!(pageIO instanceof BPlusIO))
throw new IgniteException("Not-BPlus page found, pageId=" + pageId + ", level=" + i);
ioStat.compute(pageIO.getClass(), (k, v) -> v == null ? 1 : v + 1);
if (pageIO instanceof BPlusLeafIO) {
PageIOProcessor ioProcessor = getIOProcessor(pageIO);
PageContent pageContent = ioProcessor.getContent(pageIO, addr, pageId, treeCtx);
pageContent.items.forEach(itemStorage::add);
}
pageId = ((BPlusIO) pageIO).getForward(addr);
} catch (Throwable e) {
errors.computeIfAbsent(pageId, k -> new LinkedList<>()).add(e);
pageId = 0;
}
}
}
} catch (Throwable e) {
errors.computeIfAbsent(rootPageId, k -> new LinkedList<>()).add(e);
} finally {
freeBuffer(buf);
}
return new TreeTraversalInfo(ioStat, errors, null, rootPageId, itemStorage);
}
use of org.apache.ignite.internal.processors.cache.persistence.tree.io.BPlusIO in project ignite by apache.
the class BPlusTreeSelfTest method testSizeForPutRmvSequential.
/**
* Verifies that {@link BPlusTree#size} and {@link BPlusTree#size} methods behave correctly
* on single-threaded addition and removal of elements in random order.
*
* @throws IgniteCheckedException If failed.
*/
@Test
public void testSizeForPutRmvSequential() throws IgniteCheckedException {
MAX_PER_PAGE = 5;
boolean DEBUG_PRINT = false;
int itemCnt = (int) Math.pow(MAX_PER_PAGE, 5) + rnd.nextInt(MAX_PER_PAGE * MAX_PER_PAGE);
Long[] items = new Long[itemCnt];
for (int i = 0; i < itemCnt; ++i) items[i] = (long) i;
TestTree testTree = createTestTree(true);
TreeMap<Long, Long> goldenMap = new TreeMap<>();
assertEquals(0, testTree.size());
assertEquals(0, goldenMap.size());
final Predicate<Long> rowMatcher = new Predicate<Long>() {
@Override
public boolean test(Long row) {
return row % 7 == 0;
}
};
final BPlusTree.TreeRowClosure<Long, Long> rowClosure = new BPlusTree.TreeRowClosure<Long, Long>() {
@Override
public boolean apply(BPlusTree<Long, Long> tree, BPlusIO<Long> io, long pageAddr, int idx) throws IgniteCheckedException {
return rowMatcher.test(io.getLookupRow(tree, pageAddr, idx));
}
};
int correctMatchingRows = 0;
Collections.shuffle(Arrays.asList(items), rnd);
for (Long row : items) {
if (DEBUG_PRINT) {
X.println(" --> put(" + row + ")");
X.print(testTree.printTree());
}
assertEquals(goldenMap.put(row, row), testTree.put(row));
assertEquals(row, testTree.findOne(row));
if (rowMatcher.test(row))
++correctMatchingRows;
assertEquals(correctMatchingRows, testTree.size(rowClosure));
long correctSize = goldenMap.size();
assertEquals(correctSize, testTree.size());
assertEquals(correctSize, size(testTree.find(null, null)));
assertNoLocks();
}
Collections.shuffle(Arrays.asList(items), rnd);
for (Long row : items) {
if (DEBUG_PRINT) {
X.println(" --> rmv(" + row + ")");
X.print(testTree.printTree());
}
assertEquals(row, goldenMap.remove(row));
assertEquals(row, testTree.remove(row));
assertNull(testTree.findOne(row));
if (rowMatcher.test(row))
--correctMatchingRows;
assertEquals(correctMatchingRows, testTree.size(rowClosure));
long correctSize = goldenMap.size();
assertEquals(correctSize, testTree.size());
assertEquals(correctSize, size(testTree.find(null, null)));
assertNoLocks();
}
}
Aggregations