/**
   * This case results in a single root leaf filled to capacity.
   *
   * @throws IOException
   */
  public void test_buildOrder10() throws Exception {

    final BTree btree = getProblem1();

    doBuildAndDiscardCache(btree, 10 /* m */);

    /*
     * Verify that we can load the index file and that the metadata
     * associated with the index file is correct (we are only checking those
     * aspects that are easily defined by the test case and not, for
     * example, those aspects that depend on the specifics of the length of
     * serialized nodes or leaves).
     */

    final IndexSegmentStore segStore = new IndexSegmentStore(outFile);

    assertEquals("#nodes", 0, segStore.getCheckpoint().nnodes);
    assertEquals("#leaves", 1, segStore.getCheckpoint().nleaves);
    assertEquals("#entries", 10, segStore.getCheckpoint().nentries);
    assertEquals("height", 0, segStore.getCheckpoint().height);
    assertEquals(segStore.getCheckpoint().addrRoot, segStore.getCheckpoint().addrFirstLeaf);
    assertEquals(segStore.getCheckpoint().addrFirstLeaf, segStore.getCheckpoint().addrLastLeaf);

    final IndexSegment seg = segStore.loadIndexSegment();

    try {

      assertEquals(10, seg.getBranchingFactor());
      assertEquals(0, seg.getHeight());
      assertEquals(1, seg.getLeafCount());
      assertEquals(0, seg.getNodeCount());
      assertEquals(10, seg.getEntryCount());

      final ImmutableLeaf leaf = seg.readLeaf(segStore.getCheckpoint().addrRoot);
      assertEquals("priorAddr", 0L, leaf.getPriorAddr());
      assertEquals("nextAddr", 0L, leaf.getNextAddr());

      final ImmutableLeafCursor itr = seg.newLeafCursor(SeekEnum.First);
      //        if(LRUNexus.INSTANCE!=null)
      //        assertTrue(leaf.getDelegate() == itr.leaf().getDelegate()); // Note: test depends on
      // cache.
      assertNull(itr.prior());
      assertNull(itr.next());

      // test index segment structure.
      dumpIndexSegment(seg);

      /*
       * verify the right keys in the right leaves.
       */
      {
        Leaf root = (Leaf) seg.getRoot();
        assertKeys(new int[] {1, 2, 3, 4, 5, 6, 7, 8, 9, 10}, root);
      }

      /*
       * Verify the total index order.
       */
      assertSameBTree(btree, seg);

    } finally {

      // close so we can delete the backing store.
      seg.close();
    }
  }
  /**
   * This case results in a root node and two leaves. Each leaf is at its minimum capacity (5). This
   * tests an edge case for the algorithm that distributes the keys among the leaves when there
   * would otherwise be an underflow in the last leaf.
   *
   * @throws IOException
   */
  public void test_buildOrder9() throws Exception {

    final BTree btree = getProblem1();

    doBuildAndDiscardCache(btree, 9 /*m*/);

    //        final long commitTime = System.currentTimeMillis();
    //
    //        IndexSegmentBuilder.newInstance(outFile, tmpDir, btree.getEntryCount(), btree
    //                .rangeIterator(), 9/* m */, btree.getIndexMetadata(), commitTime,
    //                true/*compactingMerge*/,bufferNodes).call();

    /*
     * Verify that we can load the index file and that the metadata
     * associated with the index file is correct (we are only checking those
     * aspects that are easily defined by the test case and not, for
     * example, those aspects that depend on the specifics of the length of
     * serialized nodes or leaves).
     */
    final IndexSegmentStore segStore = new IndexSegmentStore(outFile);

    assertEquals("#nodes", 1, segStore.getCheckpoint().nnodes);
    assertEquals("#leaves", 2, segStore.getCheckpoint().nleaves);
    assertEquals("#entries", 10, segStore.getCheckpoint().nentries);
    assertEquals("height", 1, segStore.getCheckpoint().height);
    assertNotSame(segStore.getCheckpoint().addrRoot, segStore.getCheckpoint().addrFirstLeaf);
    assertNotSame(segStore.getCheckpoint().addrFirstLeaf, segStore.getCheckpoint().addrLastLeaf);

    final IndexSegment seg = segStore.loadIndexSegment();

    try {

      assertEquals(9, seg.getBranchingFactor());
      assertEquals(1, seg.getHeight());
      assertEquals(2, seg.getLeafCount());
      assertEquals(1, seg.getNodeCount());
      assertEquals(10, seg.getEntryCount());

      final ImmutableLeaf firstLeaf = seg.readLeaf(segStore.getCheckpoint().addrFirstLeaf);

      assertEquals("priorAddr", 0L, firstLeaf.getPriorAddr());

      assertEquals("nextAddr", segStore.getCheckpoint().addrLastLeaf, firstLeaf.getNextAddr());

      final ImmutableLeaf lastLeaf = seg.readLeaf(segStore.getCheckpoint().addrLastLeaf);

      assertEquals("priorAddr", segStore.getCheckpoint().addrFirstLeaf, lastLeaf.getPriorAddr());

      assertEquals("nextAddr", 0L, lastLeaf.getNextAddr());

      // test forward scan
      {
        final ImmutableLeafCursor itr = seg.newLeafCursor(SeekEnum.First);

        //            if(LRUNexus.INSTANCE!=null)
        //            assertTrue(firstLeaf.getDelegate() == itr.leaf().getDelegate()); // Note: test
        // depends on cache!
        assertNull(itr.prior());

        //            if(LRUNexus.INSTANCE!=null)
        //            assertTrue(lastLeaf.getDelegate() == itr.next().getDelegate()); // Note: test
        // depends on cache!

        //            if(LRUNexus.INSTANCE!=null)
        //            assertTrue(lastLeaf.getDelegate() == itr.leaf().getDelegate()); // Note: test
        // depends on cache!

      }

      /*
       * test reverse scan
       *
       * Note: the scan starts with the last leaf in the key order and then
       * proceeds in reverse key order.
       */
      {
        final ImmutableLeafCursor itr = seg.newLeafCursor(SeekEnum.Last);

        //            if(LRUNexus.INSTANCE!=null)
        //            assertTrue(lastLeaf.getDelegate() == itr.leaf().getDelegate()); // Note: test
        // depends on cache!
        assertNull(itr.next());

        //            if(LRUNexus.INSTANCE!=null)
        //            assertTrue(firstLeaf.getDelegate() == itr.prior().getDelegate()); // Note:
        // test depends on cache!
        //            if(LRUNexus.INSTANCE!=null)
        //            assertTrue(firstLeaf.getDelegate() == itr.leaf().getDelegate()); // Note: test
        // depends on cache!

      }

      // test index segment structure.
      dumpIndexSegment(seg);

      /*
       * Test the tree in detail.
       */
      {
        final Node A = (Node) seg.getRoot();
        final Leaf a = (Leaf) A.getChild(0);
        final Leaf b = (Leaf) A.getChild(1);

        assertKeys(new int[] {6}, A);
        assertEntryCounts(new int[] {5, 5}, A);

        assertKeys(new int[] {1, 2, 3, 4, 5}, a);
        assertKeys(new int[] {6, 7, 8, 9, 10}, b);

        // Note: values are verified by testing the total order.

      }

      /*
       * Verify the total index order.
       */
      assertSameBTree(btree, seg);

    } finally {

      // close so we can delete the backing store.
      seg.close();
    }
  }