public SortedInvertedIndexReader(File file, int cardinality, boolean isMmap) throws IOException {
   this.cardinality = cardinality;
   if (isMmap) {
     indexReader =
         FixedByteSingleValueMultiColReader.forMmap(file, cardinality, 2, new int[] {4, 4});
   } else {
     indexReader =
         FixedByteSingleValueMultiColReader.forHeap(file, cardinality, 2, new int[] {4, 4});
   }
 }
 @Override
 public boolean unload() throws Exception {
   indexFileReader.close();
   dictionaryReader.close();
   forwardIndexReader.close();
   return true;
 }
 @Override
 public int[] getMinMaxRangeFor(int dictId) {
   int[] ret = new int[2];
   if (dictId >= cardinality) {
     return ret;
   }
   ret[0] = indexReader.getInt(dictId, 0);
   ret[1] = indexReader.getInt(dictId, 1);
   return ret;
 }
 @Override
 public ImmutableRoaringBitmap getImmutable(int idx) {
   if (idx >= cardinality) {
     return new MutableRoaringBitmap();
   }
   MutableRoaringBitmap rr = new MutableRoaringBitmap();
   int min = indexReader.getInt(idx, 0);
   int max = indexReader.getInt(idx, 1);
   for (int i = min; i <= max; i++) {
     rr.add(i);
   }
   return rr;
 }
 @Override
 public void close() throws IOException {
   indexReader.close();
 }
 public SortedInvertedIndexReader(FixedByteSingleValueMultiColReader indexReader) {
   this.indexReader = indexReader;
   this.cardinality = indexReader.getNumberOfRows();
 }