[NO ISSUE][RT] Eliminate Excessive Object Creation in Sort Merge

- user model changes: no
- storage format changes: no
- interface changes: no

Details:
- Currently, every binary search for frame lookup during
  the sort merge phase results in auto-boxing to an Integer.
  In addition, every call to InnerFrameInfo#compareTo during
  the binary search results another auto-boxing. This change
  eliminates these objects creation by using a MutableInt and
  and using a primitive int comparison while comparing.

Change-Id: I72b498d476d242f85966caf67d2543978e5c88bb
Reviewed-on: https://asterix-gerrit.ics.uci.edu/3276
Integration-Tests: Jenkins <jenkins@fulliautomatix.ics.uci.edu>
Reviewed-by: Michael Blow <mblow@apache.org>
Tested-by: Jenkins <jenkins@fulliautomatix.ics.uci.edu>
Contrib: Jenkins <jenkins@fulliautomatix.ics.uci.edu>
diff --git a/hyracks-fullstack/hyracks/hyracks-dataflow-std/src/main/java/org/apache/hyracks/dataflow/std/sort/util/GroupFrameAccessor.java b/hyracks-fullstack/hyracks/hyracks-dataflow-std/src/main/java/org/apache/hyracks/dataflow/std/sort/util/GroupFrameAccessor.java
index bf61435..1e3f73e 100644
--- a/hyracks-fullstack/hyracks/hyracks-dataflow-std/src/main/java/org/apache/hyracks/dataflow/std/sort/util/GroupFrameAccessor.java
+++ b/hyracks-fullstack/hyracks/hyracks-dataflow-std/src/main/java/org/apache/hyracks/dataflow/std/sort/util/GroupFrameAccessor.java
@@ -24,6 +24,7 @@
 import java.util.Collections;
 import java.util.List;
 
+import org.apache.commons.lang3.mutable.MutableInt;
 import org.apache.hyracks.api.comm.FrameHelper;
 import org.apache.hyracks.api.comm.IFrameTupleAccessor;
 import org.apache.hyracks.api.dataflow.value.RecordDescriptor;
@@ -37,7 +38,7 @@
  */
 public class GroupFrameAccessor implements IFrameTupleAccessor {
 
-    private class InnerFrameInfo implements Comparable<Integer> {
+    private class InnerFrameInfo implements Comparable<MutableInt> {
         int start;
         int length;
         int tupleCount;
@@ -49,27 +50,29 @@
         }
 
         @Override
-        public int compareTo(Integer o) {
-            return -o.compareTo(tupleCount);
+        public int compareTo(MutableInt other) {
+            return -Integer.compare(other.intValue(), tupleCount);
         }
     }
 
     private final RecordDescriptor recordDescriptor;
     private final int minFrameSize;
     private final FrameTupleAccessor frameTupleAccessor;
+    private final List<InnerFrameInfo> innerFrameInfos;
+    private final MutableInt binarySearchKey;
     private int lastFrameId;
     // the start tuple index of the last accessed frame (inclusive)
     private int lastFrameStart;
     // the end tuple index of the last accessed frame (exclusive)
     private int lastFrameEnd;
     private ByteBuffer buffer;
-    private final List<InnerFrameInfo> innerFrameInfos;
 
     public GroupFrameAccessor(int minFrameSize, RecordDescriptor recordDescriptor) {
         this.minFrameSize = minFrameSize;
         this.recordDescriptor = (recordDescriptor);
         this.frameTupleAccessor = new FrameTupleAccessor(recordDescriptor);
         this.innerFrameInfos = new ArrayList<>();
+        binarySearchKey = new MutableInt();
     }
 
     @Override
@@ -164,7 +167,8 @@
             return tupleIndex - lastFrameStart;
         }
         // we perform binary search to get the frame Id
-        int subFrameId = Collections.binarySearch(innerFrameInfos, tupleIndex);
+        binarySearchKey.setValue(tupleIndex);
+        int subFrameId = Collections.binarySearch(innerFrameInfos, binarySearchKey);
         if (subFrameId >= 0) {
             subFrameId++;
         } else {
@@ -174,7 +178,6 @@
         lastFrameId = subFrameId;
         lastFrameStart = lastFrameId > 0 ? innerFrameInfos.get(lastFrameId - 1).tupleCount : 0;
         lastFrameEnd = innerFrameInfos.get(lastFrameId).tupleCount;
-
         return tupleIndex - lastFrameStart;
     }