1/* 2 * Copyright (C) 2013 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License 15 */ 16 17package benchmarks; 18 19import com.google.caliper.Param; 20import com.google.caliper.SimpleBenchmark; 21 22import java.lang.reflect.Array; 23import java.lang.reflect.Constructor; 24import java.util.Arrays; 25 26public class DeepArrayOpsBenchmark extends SimpleBenchmark { 27 @Param({"1", "4", "16", "256", "2048"}) int arrayLength; 28 29 private Object[] array; 30 private Object[] array2; 31 32 private Object[] array3; 33 private Object[] array4; 34 35 protected void setUp() throws Exception { 36 array = new Object[arrayLength * 13]; 37 array2 = new Object[arrayLength * 13]; 38 for (int i = 0; i < arrayLength; i += 13) { 39 array[i] = new IntWrapper(i); 40 array2[i] = new IntWrapper(i); 41 42 array[i + 1] = new16ElementObjectarray(); 43 array2[i + 1] = new16ElementObjectarray(); 44 45 array[i + 2] = new boolean[16]; 46 array2[i + 2] = new boolean[16]; 47 48 array[i + 3] = new byte[16]; 49 array2[i + 3] = new byte[16]; 50 51 array[i + 4] = new char[16]; 52 array2[i + 4] = new char[16]; 53 54 array[i + 5] = new short[16]; 55 array2[i + 5] = new short[16]; 56 57 array[i + 6] = new float[16]; 58 array2[i + 6] = new float[16]; 59 60 array[i + 7] = new long[16]; 61 array2[i + 7] = new long[16]; 62 63 array[i + 8] = new int[16]; 64 array2[i + 8] = new int[16]; 65 66 array[i + 9] = new double[16]; 67 array2[i + 9] = new double[16]; 68 69 // Subarray types are concrete objects. 70 array[i + 10] = new16ElementArray(String.class, String.class); 71 array2[i + 10] = new16ElementArray(String.class, String.class); 72 73 array[i + 11] = new16ElementArray(Integer.class, Integer.class); 74 array2[i + 11] = new16ElementArray(Integer.class, Integer.class); 75 76 // Subarray types is an interface. 77 array[i + 12] = new16ElementArray(CharSequence.class, String.class); 78 array2[i + 12] = new16ElementArray(CharSequence.class, String.class); 79 } 80 } 81 82 public void timeDeepHashCode(int reps) { 83 for (int i = 0; i < reps; ++i) { 84 Arrays.deepHashCode(array); 85 } 86 } 87 88 public void timeEquals(int reps) { 89 for (int i = 0; i < reps; ++i) { 90 Arrays.deepEquals(array, array2); 91 } 92 } 93 94 private static final Object[] new16ElementObjectarray() { 95 Object[] array = new Object[16]; 96 for (int i = 0; i < 16; ++i) { 97 array[i] = new IntWrapper(i); 98 } 99 100 return array; 101 } 102 103 @SuppressWarnings("unchecked") 104 private static final <T, V> T[] new16ElementArray(Class<T> arrayType, Class<V> type) 105 throws Exception { 106 T[] array = (T []) Array.newInstance(type, 16); 107 if (!arrayType.isAssignableFrom(type)) { 108 throw new IllegalArgumentException(arrayType + " is not assignable from " + type); 109 } 110 111 Constructor<V> constructor = type.getDeclaredConstructor(String.class); 112 for (int i = 0; i < 16; ++i) { 113 array[i] = (T) constructor.newInstance(String.valueOf(i + 1000)); 114 } 115 116 return array; 117 } 118 119 /** 120 * A class that provides very basic equals() and hashCode() operations 121 * and doesn't resort to memoization tricks like {@link java.lang.Integer}. 122 * 123 * Useful for providing equal objects that aren't the same (a.equals(b) but 124 * a != b). 125 */ 126 public static final class IntWrapper { 127 private final int wrapped; 128 129 public IntWrapper(int wrap) { 130 wrapped = wrap; 131 } 132 133 @Override 134 public int hashCode() { 135 return wrapped; 136 } 137 138 @Override 139 public boolean equals(Object o) { 140 if (!(o instanceof IntWrapper)) { 141 return false; 142 } 143 144 return ((IntWrapper) o).wrapped == this.wrapped; 145 } 146 } 147} 148 149