public void seekToField(int fieldId) {
   int startOffset =
       accessor.getFieldSlotsLength()
           + accessor.getTupleStartOffset(tupleId)
           + accessor.getFieldStartOffset(tupleId, fieldId);
   //                Rt.p(accessor.getFieldSlotsLength() +" "+
   // accessor.getTupleStartOffset(tupleId)
   //                        +" "+ accessor.getFieldStartOffset(tupleId, fieldId));
   in.setByteBuffer(accessor.getBuffer(), startOffset);
 }
  static int assertFTADataIsSorted(
      IFrameTupleAccessor fta, Map<Integer, String> keyValuePair, int preKey)
      throws HyracksDataException {

    ByteBufferInputStream bbis = new ByteBufferInputStream();
    DataInputStream di = new DataInputStream(bbis);
    for (int i = 0; i < fta.getTupleCount(); i++) {
      bbis.setByteBuffer(
          fta.getBuffer(),
          fta.getTupleStartOffset(i) + fta.getFieldStartOffset(i, 0) + fta.getFieldSlotsLength());
      int key = (int) RecordDesc.getFields()[0].deserialize(di);
      bbis.setByteBuffer(
          fta.getBuffer(),
          fta.getTupleStartOffset(i) + fta.getFieldStartOffset(i, 1) + fta.getFieldSlotsLength());
      String value = (String) RecordDesc.getFields()[1].deserialize(di);

      if (!keyValuePair.get(key).equals(value)) {
        assertTrue(false);
      }
      keyValuePair.remove(key);
      assertTrue(key >= preKey);
      preKey = key;
    }
    return preKey;
  }
 public boolean nextTuple() {
   tupleId++;
   while (tupleId >= tupleCount) {
     if (!input.hasNext()) {
       return false;
     }
     ByteBuffer buf = input.next();
     accessor.reset(buf);
     tupleId = 0;
     tupleCount = accessor.getTupleCount();
   }
   seekToField(0);
   return true;
 }
  private void readKeyValue(IFrameTupleReference tuple) throws HyracksDataException {
    FrameTupleReference ftr = (FrameTupleReference) tuple;
    IFrameTupleAccessor fta = ftr.getFrameTupleAccessor();
    ByteBuffer buffer = fta.getBuffer();
    int tIndex = ftr.getTupleIndex();

    int keyStart =
        fta.getFieldSlotsLength()
            + fta.getTupleStartOffset(tIndex)
            + fta.getFieldStartOffset(tIndex, 0);
    int valueStart =
        fta.getFieldSlotsLength()
            + fta.getTupleStartOffset(tIndex)
            + fta.getFieldStartOffset(tIndex, 1);

    keyInputStream.setByteBuffer(buffer, keyStart);
    valueInputStream.setByteBuffer(buffer, valueStart);

    try {
      // read key if necessary
      if (!skipKey) {
        key.readFields(keyInput);
      }
      // read value
      value.readFields(valueInput);
    } catch (Exception e) {
      throw new HyracksDataException(e);
    }
  }
  static void assertReadSorted(
      List<RunAndMaxFrameSizePair> runs,
      IFrameTupleAccessor fta,
      IFrame frame,
      Map<Integer, String> keyValuePair)
      throws HyracksDataException {

    assertTrue(runs.size() > 0);
    for (RunAndMaxFrameSizePair run : runs) {
      run.run.open();
      int preKey = Integer.MIN_VALUE;
      while (run.run.nextFrame(frame)) {
        fta.reset(frame.getBuffer());
        preKey = assertFTADataIsSorted(fta, keyValuePair, preKey);
      }
      run.run.close();
    }
    assertTrue(keyValuePair.isEmpty());
  }
  public TupleReader(IFrameTupleAccessor accessor, ByteBufferInputStream in, int tupleId) {
    super(in);
    this.input =
        new Iterator<ByteBuffer>() {
          @Override
          public void remove() {}

          @Override
          public ByteBuffer next() {
            return null;
          }

          @Override
          public boolean hasNext() {
            return false;
          }
        };
    this.accessor = accessor;
    this.in = in;
    this.tupleId = tupleId;
    tupleCount = accessor.getTupleCount();
  }
 public void dump() {
   Rt.p(Rt.getHex(0, accessor.getBuffer().array(), 0, 256, false));
 }
 public int getFieldLength(int fieldId) {
   return accessor.getFieldLength(tupleId, fieldId);
 }
 public int getFieldCount() {
   return accessor.getFieldCount();
 }