public static SkippR fastSkip()

in core/src/main/java/org/apache/accumulo/core/file/rfile/RelativeKey.java [218:433]


  public static SkippR fastSkip(DataInput in, Key seekKey, ArrayByteSequence value, Key prevKey,
      Key currKey, int entriesLeft) throws IOException {
    // this method mostly avoids object allocation and only does compares when the row changes

    ArrayByteSequence row, cf, cq, cv;
    ArrayByteSequence prow, pcf, pcq, pcv;

    ByteSequence stopRow = seekKey.getRowData();
    ByteSequence stopCF = seekKey.getColumnFamilyData();
    ByteSequence stopCQ = seekKey.getColumnQualifierData();

    long ts = -1;
    long pts = -1;
    boolean pdel = false;

    int rowCmp = -1, cfCmp = -1, cqCmp = -1;

    if (currKey != null) {

      prow = new ArrayByteSequence(currKey.getRowData());
      pcf = new ArrayByteSequence(currKey.getColumnFamilyData());
      pcq = new ArrayByteSequence(currKey.getColumnQualifierData());
      pcv = new ArrayByteSequence(currKey.getColumnVisibilityData());
      pts = currKey.getTimestamp();

      row = new ArrayByteSequence(currKey.getRowData());
      cf = new ArrayByteSequence(currKey.getColumnFamilyData());
      cq = new ArrayByteSequence(currKey.getColumnQualifierData());
      cv = new ArrayByteSequence(currKey.getColumnVisibilityData());
      ts = currKey.getTimestamp();

      rowCmp = row.compareTo(stopRow);
      cfCmp = cf.compareTo(stopCF);
      cqCmp = cq.compareTo(stopCQ);

      if (rowCmp >= 0) {
        if (rowCmp > 0) {
          RelativeKey rk = new RelativeKey();
          rk.key = rk.prevKey = new Key(currKey);
          return new SkippR(rk, 0, prevKey);
        }

        if (cfCmp >= 0) {
          if (cfCmp > 0) {
            RelativeKey rk = new RelativeKey();
            rk.key = rk.prevKey = new Key(currKey);
            return new SkippR(rk, 0, prevKey);
          }

          if (cqCmp >= 0) {
            RelativeKey rk = new RelativeKey();
            rk.key = rk.prevKey = new Key(currKey);
            return new SkippR(rk, 0, prevKey);
          }
        }
      }

    } else {
      row = new ArrayByteSequence(new byte[64], 0, 0);
      cf = new ArrayByteSequence(new byte[64], 0, 0);
      cq = new ArrayByteSequence(new byte[64], 0, 0);
      cv = new ArrayByteSequence(new byte[64], 0, 0);

      prow = new ArrayByteSequence(new byte[64], 0, 0);
      pcf = new ArrayByteSequence(new byte[64], 0, 0);
      pcq = new ArrayByteSequence(new byte[64], 0, 0);
      pcv = new ArrayByteSequence(new byte[64], 0, 0);
    }

    byte fieldsSame = -1;
    byte fieldsPrefixed = 0;
    int count = 0;
    Key newPrevKey = null;

    while (count < entriesLeft) {

      pdel = (fieldsSame & DELETED) == DELETED;

      fieldsSame = in.readByte();
      if ((fieldsSame & PREFIX_COMPRESSION_ENABLED) == PREFIX_COMPRESSION_ENABLED) {
        fieldsPrefixed = in.readByte();
      } else {
        fieldsPrefixed = 0;
      }

      boolean changed = false;

      if ((fieldsSame & ROW_SAME) != ROW_SAME) {

        ArrayByteSequence tmp = prow;
        prow = row;
        row = tmp;

        if ((fieldsPrefixed & ROW_COMMON_PREFIX) == ROW_COMMON_PREFIX) {
          readPrefix(in, row, prow);
        } else {
          read(in, row);
        }

        // read a new row, so need to compare...
        rowCmp = row.compareTo(stopRow);
        changed = true;
      } // else the row is the same as the last, so no need to compare

      if ((fieldsSame & CF_SAME) != CF_SAME) {

        ArrayByteSequence tmp = pcf;
        pcf = cf;
        cf = tmp;

        if ((fieldsPrefixed & CF_COMMON_PREFIX) == CF_COMMON_PREFIX) {
          readPrefix(in, cf, pcf);
        } else {
          read(in, cf);
        }

        cfCmp = cf.compareTo(stopCF);
        changed = true;
      }

      if ((fieldsSame & CQ_SAME) != CQ_SAME) {

        ArrayByteSequence tmp = pcq;
        pcq = cq;
        cq = tmp;

        if ((fieldsPrefixed & CQ_COMMON_PREFIX) == CQ_COMMON_PREFIX) {
          readPrefix(in, cq, pcq);
        } else {
          read(in, cq);
        }

        cqCmp = cq.compareTo(stopCQ);
        changed = true;
      }

      if ((fieldsSame & CV_SAME) != CV_SAME) {

        ArrayByteSequence tmp = pcv;
        pcv = cv;
        cv = tmp;

        if ((fieldsPrefixed & CV_COMMON_PREFIX) == CV_COMMON_PREFIX) {
          readPrefix(in, cv, pcv);
        } else {
          read(in, cv);
        }
      }

      if ((fieldsSame & TS_SAME) != TS_SAME) {
        pts = ts;

        if ((fieldsPrefixed & TS_DIFF) == TS_DIFF) {
          ts = WritableUtils.readVLong(in) + pts;
        } else {
          ts = WritableUtils.readVLong(in);
        }
      }

      readValue(in, value);

      count++;

      if (changed && rowCmp >= 0) {
        if (rowCmp > 0) {
          break;
        }

        if (cfCmp >= 0) {
          if (cfCmp > 0) {
            break;
          }

          if (cqCmp >= 0) {
            break;
          }
        }
      }

    }

    if (count > 1) {
      ArrayByteSequence trow, tcf, tcq, tcv;
      long tts;

      // when the current keys field is same as the last, then
      // set the prev keys field the same as the current key
      trow = (fieldsSame & ROW_SAME) == ROW_SAME ? row : prow;
      tcf = (fieldsSame & CF_SAME) == CF_SAME ? cf : pcf;
      tcq = (fieldsSame & CQ_SAME) == CQ_SAME ? cq : pcq;
      tcv = (fieldsSame & CV_SAME) == CV_SAME ? cv : pcv;
      tts = (fieldsSame & TS_SAME) == TS_SAME ? ts : pts;

      newPrevKey = new Key(trow.getBackingArray(), trow.offset(), trow.length(),
          tcf.getBackingArray(), tcf.offset(), tcf.length(), tcq.getBackingArray(), tcq.offset(),
          tcq.length(), tcv.getBackingArray(), tcv.offset(), tcv.length(), tts);
      newPrevKey.setDeleted(pdel);
    } else if (count == 1) {
      if (currKey != null) {
        newPrevKey = currKey;
      } else {
        newPrevKey = prevKey;
      }
    } else {
      throw new IllegalStateException();
    }

    RelativeKey result = new RelativeKey();
    result.key = new Key(row.getBackingArray(), row.offset(), row.length(), cf.getBackingArray(),
        cf.offset(), cf.length(), cq.getBackingArray(), cq.offset(), cq.length(),
        cv.getBackingArray(), cv.offset(), cv.length(), ts);
    result.key.setDeleted((fieldsSame & DELETED) != 0);
    result.prevKey = result.key;

    return new SkippR(result, count, newPrevKey);
  }