| OLD | NEW |
| 1 // Protocol Buffers - Google's data interchange format | 1 // Protocol Buffers - Google's data interchange format |
| 2 // Copyright 2008 Google Inc. All rights reserved. | 2 // Copyright 2008 Google Inc. All rights reserved. |
| 3 // https://developers.google.com/protocol-buffers/ | 3 // https://developers.google.com/protocol-buffers/ |
| 4 // | 4 // |
| 5 // Redistribution and use in source and binary forms, with or without | 5 // Redistribution and use in source and binary forms, with or without |
| 6 // modification, are permitted provided that the following conditions are | 6 // modification, are permitted provided that the following conditions are |
| 7 // met: | 7 // met: |
| 8 // | 8 // |
| 9 // * Redistributions of source code must retain the above copyright | 9 // * Redistributions of source code must retain the above copyright |
| 10 // notice, this list of conditions and the following disclaimer. | 10 // notice, this list of conditions and the following disclaimer. |
| (...skipping 20 matching lines...) Expand all Loading... |
| 31 package com.google.protobuf; | 31 package com.google.protobuf; |
| 32 | 32 |
| 33 import com.google.protobuf.Internal.DoubleList; | 33 import com.google.protobuf.Internal.DoubleList; |
| 34 | 34 |
| 35 import java.util.Arrays; | 35 import java.util.Arrays; |
| 36 import java.util.Collection; | 36 import java.util.Collection; |
| 37 import java.util.RandomAccess; | 37 import java.util.RandomAccess; |
| 38 | 38 |
| 39 /** | 39 /** |
| 40 * An implementation of {@link DoubleList} on top of a primitive array. | 40 * An implementation of {@link DoubleList} on top of a primitive array. |
| 41 * | 41 * |
| 42 * @author dweis@google.com (Daniel Weis) | 42 * @author dweis@google.com (Daniel Weis) |
| 43 */ | 43 */ |
| 44 final class DoubleArrayList | 44 final class DoubleArrayList |
| 45 extends AbstractProtobufList<Double> | 45 extends AbstractProtobufList<Double> implements DoubleList, RandomAccess { |
| 46 implements DoubleList, RandomAccess { | 46 |
| 47 | |
| 48 private static final DoubleArrayList EMPTY_LIST = new DoubleArrayList(); | 47 private static final DoubleArrayList EMPTY_LIST = new DoubleArrayList(); |
| 49 static { | 48 static { |
| 50 EMPTY_LIST.makeImmutable(); | 49 EMPTY_LIST.makeImmutable(); |
| 51 } | 50 } |
| 52 | 51 |
| 53 public static DoubleArrayList emptyList() { | 52 public static DoubleArrayList emptyList() { |
| 54 return EMPTY_LIST; | 53 return EMPTY_LIST; |
| 55 } | 54 } |
| 56 | 55 |
| 57 /** | 56 /** |
| 58 * The backing store for the list. | 57 * The backing store for the list. |
| 59 */ | 58 */ |
| 60 private double[] array; | 59 private double[] array; |
| 61 | 60 |
| 62 /** | 61 /** |
| 63 * The size of the list distinct from the length of the array. That is, it is
the number of | 62 * The size of the list distinct from the length of the array. That is, it is
the number of |
| 64 * elements set in the list. | 63 * elements set in the list. |
| 65 */ | 64 */ |
| 66 private int size; | 65 private int size; |
| 67 | 66 |
| 68 /** | 67 /** |
| 69 * Constructs a new mutable {@code DoubleArrayList} with default capacity. | 68 * Constructs a new mutable {@code DoubleArrayList} with default capacity. |
| 70 */ | 69 */ |
| 71 DoubleArrayList() { | 70 DoubleArrayList() { |
| 72 this(new double[DEFAULT_CAPACITY], 0); | 71 this(new double[DEFAULT_CAPACITY], 0); |
| 73 } | 72 } |
| 74 | 73 |
| 75 /** | 74 /** |
| 76 * Constructs a new mutable {@code DoubleArrayList} | 75 * Constructs a new mutable {@code DoubleArrayList} containing the same elemen
ts as {@code other}. |
| 77 * containing the same elements as {@code other}. | |
| 78 */ | 76 */ |
| 79 private DoubleArrayList(double[] other, int size) { | 77 private DoubleArrayList(double[] array, int size) { |
| 80 array = other; | 78 this.array = array; |
| 81 this.size = size; | 79 this.size = size; |
| 82 } | 80 } |
| 83 | 81 |
| 84 @Override | 82 @Override |
| 85 public boolean equals(Object o) { | 83 public boolean equals(Object o) { |
| 86 if (this == o) { | 84 if (this == o) { |
| 87 return true; | 85 return true; |
| 88 } | 86 } |
| 89 if (!(o instanceof DoubleArrayList)) { | 87 if (!(o instanceof DoubleArrayList)) { |
| 90 return super.equals(o); | 88 return super.equals(o); |
| 91 } | 89 } |
| 92 DoubleArrayList other = (DoubleArrayList) o; | 90 DoubleArrayList other = (DoubleArrayList) o; |
| 93 if (size != other.size) { | 91 if (size != other.size) { |
| 94 return false; | 92 return false; |
| 95 } | 93 } |
| 96 | 94 |
| 97 final double[] arr = other.array; | 95 final double[] arr = other.array; |
| 98 for (int i = 0; i < size; i++) { | 96 for (int i = 0; i < size; i++) { |
| 99 if (array[i] != arr[i]) { | 97 if (array[i] != arr[i]) { |
| 100 return false; | 98 return false; |
| 101 } | 99 } |
| 102 } | 100 } |
| 103 | 101 |
| 104 return true; | 102 return true; |
| 105 } | 103 } |
| 106 | 104 |
| 107 @Override | 105 @Override |
| 108 public int hashCode() { | 106 public int hashCode() { |
| 109 int result = 1; | 107 int result = 1; |
| 110 for (int i = 0; i < size; i++) { | 108 for (int i = 0; i < size; i++) { |
| 111 long bits = Double.doubleToLongBits(array[i]); | 109 long bits = Double.doubleToLongBits(array[i]); |
| 112 result = (31 * result) + Internal.hashLong(bits); | 110 result = (31 * result) + Internal.hashLong(bits); |
| 113 } | 111 } |
| 114 return result; | 112 return result; |
| 115 } | 113 } |
| 116 | 114 |
| 117 @Override | 115 @Override |
| 118 public DoubleList mutableCopyWithCapacity(int capacity) { | 116 public DoubleList mutableCopyWithCapacity(int capacity) { |
| 119 if (capacity < size) { | 117 if (capacity < size) { |
| 120 throw new IllegalArgumentException(); | 118 throw new IllegalArgumentException(); |
| 121 } | 119 } |
| 122 return new DoubleArrayList(Arrays.copyOf(array, capacity), size); | 120 return new DoubleArrayList(Arrays.copyOf(array, capacity), size); |
| 123 } | 121 } |
| 124 | 122 |
| 125 @Override | 123 @Override |
| 126 public Double get(int index) { | 124 public Double get(int index) { |
| 127 return getDouble(index); | 125 return getDouble(index); |
| 128 } | 126 } |
| 129 | 127 |
| 130 @Override | 128 @Override |
| 131 public double getDouble(int index) { | 129 public double getDouble(int index) { |
| 132 ensureIndexInRange(index); | 130 ensureIndexInRange(index); |
| 133 return array[index]; | 131 return array[index]; |
| 134 } | 132 } |
| (...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 166 } | 164 } |
| 167 | 165 |
| 168 /** | 166 /** |
| 169 * Like {@link #add(int, Double)} but more efficient in that it doesn't box th
e element. | 167 * Like {@link #add(int, Double)} but more efficient in that it doesn't box th
e element. |
| 170 */ | 168 */ |
| 171 private void addDouble(int index, double element) { | 169 private void addDouble(int index, double element) { |
| 172 ensureIsMutable(); | 170 ensureIsMutable(); |
| 173 if (index < 0 || index > size) { | 171 if (index < 0 || index > size) { |
| 174 throw new IndexOutOfBoundsException(makeOutOfBoundsExceptionMessage(index)
); | 172 throw new IndexOutOfBoundsException(makeOutOfBoundsExceptionMessage(index)
); |
| 175 } | 173 } |
| 176 | 174 |
| 177 if (size < array.length) { | 175 if (size < array.length) { |
| 178 // Shift everything over to make room | 176 // Shift everything over to make room |
| 179 System.arraycopy(array, index, array, index + 1, size - index); | 177 System.arraycopy(array, index, array, index + 1, size - index); |
| 180 } else { | 178 } else { |
| 181 // Resize to 1.5x the size | 179 // Resize to 1.5x the size |
| 182 int length = ((size * 3) / 2) + 1; | 180 int length = ((size * 3) / 2) + 1; |
| 183 double[] newArray = new double[length]; | 181 double[] newArray = new double[length]; |
| 184 | 182 |
| 185 // Copy the first part directly | 183 // Copy the first part directly |
| 186 System.arraycopy(array, 0, newArray, 0, index); | 184 System.arraycopy(array, 0, newArray, 0, index); |
| 187 | 185 |
| 188 // Copy the rest shifted over by one to make room | 186 // Copy the rest shifted over by one to make room |
| 189 System.arraycopy(array, index, newArray, index + 1, size - index); | 187 System.arraycopy(array, index, newArray, index + 1, size - index); |
| 190 array = newArray; | 188 array = newArray; |
| 191 } | 189 } |
| 192 | 190 |
| 193 array[index] = element; | 191 array[index] = element; |
| 194 size++; | 192 size++; |
| 195 modCount++; | 193 modCount++; |
| 196 } | 194 } |
| 197 | 195 |
| 198 @Override | 196 @Override |
| 199 public boolean addAll(Collection<? extends Double> collection) { | 197 public boolean addAll(Collection<? extends Double> collection) { |
| 200 ensureIsMutable(); | 198 ensureIsMutable(); |
| 201 | 199 |
| 202 if (collection == null) { | 200 if (collection == null) { |
| 203 throw new NullPointerException(); | 201 throw new NullPointerException(); |
| 204 } | 202 } |
| 205 | 203 |
| 206 // We specialize when adding another DoubleArrayList to avoid boxing element
s. | 204 // We specialize when adding another DoubleArrayList to avoid boxing element
s. |
| 207 if (!(collection instanceof DoubleArrayList)) { | 205 if (!(collection instanceof DoubleArrayList)) { |
| 208 return super.addAll(collection); | 206 return super.addAll(collection); |
| 209 } | 207 } |
| 210 | 208 |
| 211 DoubleArrayList list = (DoubleArrayList) collection; | 209 DoubleArrayList list = (DoubleArrayList) collection; |
| 212 if (list.size == 0) { | 210 if (list.size == 0) { |
| 213 return false; | 211 return false; |
| 214 } | 212 } |
| 215 | 213 |
| 216 int overflow = Integer.MAX_VALUE - size; | 214 int overflow = Integer.MAX_VALUE - size; |
| 217 if (overflow < list.size) { | 215 if (overflow < list.size) { |
| 218 // We can't actually represent a list this large. | 216 // We can't actually represent a list this large. |
| 219 throw new OutOfMemoryError(); | 217 throw new OutOfMemoryError(); |
| 220 } | 218 } |
| 221 | 219 |
| 222 int newSize = size + list.size; | 220 int newSize = size + list.size; |
| 223 if (newSize > array.length) { | 221 if (newSize > array.length) { |
| 224 array = Arrays.copyOf(array, newSize); | 222 array = Arrays.copyOf(array, newSize); |
| 225 } | 223 } |
| 226 | 224 |
| 227 System.arraycopy(list.array, 0, array, size, list.size); | 225 System.arraycopy(list.array, 0, array, size, list.size); |
| 228 size = newSize; | 226 size = newSize; |
| 229 modCount++; | 227 modCount++; |
| 230 return true; | 228 return true; |
| 231 } | 229 } |
| 232 | 230 |
| 233 @Override | 231 @Override |
| 234 public boolean remove(Object o) { | 232 public boolean remove(Object o) { |
| 235 ensureIsMutable(); | 233 ensureIsMutable(); |
| 236 for (int i = 0; i < size; i++) { | 234 for (int i = 0; i < size; i++) { |
| 237 if (o.equals(array[i])) { | 235 if (o.equals(array[i])) { |
| 238 System.arraycopy(array, i + 1, array, i, size - i); | 236 System.arraycopy(array, i + 1, array, i, size - i); |
| 239 size--; | 237 size--; |
| 240 modCount++; | 238 modCount++; |
| 241 return true; | 239 return true; |
| 242 } | 240 } |
| 243 } | 241 } |
| 244 return false; | 242 return false; |
| 245 } | 243 } |
| 246 | 244 |
| 247 @Override | 245 @Override |
| 248 public Double remove(int index) { | 246 public Double remove(int index) { |
| 249 ensureIsMutable(); | 247 ensureIsMutable(); |
| 250 ensureIndexInRange(index); | 248 ensureIndexInRange(index); |
| 251 double value = array[index]; | 249 double value = array[index]; |
| 252 System.arraycopy(array, index + 1, array, index, size - index); | 250 System.arraycopy(array, index + 1, array, index, size - index); |
| 253 size--; | 251 size--; |
| 254 modCount++; | 252 modCount++; |
| 255 return value; | 253 return value; |
| 256 } | 254 } |
| 257 | 255 |
| 258 /** | 256 /** |
| 259 * Ensures that the provided {@code index} is within the range of {@code [0, s
ize]}. Throws an | 257 * Ensures that the provided {@code index} is within the range of {@code [0, s
ize]}. Throws an |
| 260 * {@link IndexOutOfBoundsException} if it is not. | 258 * {@link IndexOutOfBoundsException} if it is not. |
| 261 * | 259 * |
| 262 * @param index the index to verify is in range | 260 * @param index the index to verify is in range |
| 263 */ | 261 */ |
| 264 private void ensureIndexInRange(int index) { | 262 private void ensureIndexInRange(int index) { |
| 265 if (index < 0 || index >= size) { | 263 if (index < 0 || index >= size) { |
| 266 throw new IndexOutOfBoundsException(makeOutOfBoundsExceptionMessage(index)
); | 264 throw new IndexOutOfBoundsException(makeOutOfBoundsExceptionMessage(index)
); |
| 267 } | 265 } |
| 268 } | 266 } |
| 269 | 267 |
| 270 private String makeOutOfBoundsExceptionMessage(int index) { | 268 private String makeOutOfBoundsExceptionMessage(int index) { |
| 271 return "Index:" + index + ", Size:" + size; | 269 return "Index:" + index + ", Size:" + size; |
| 272 } | 270 } |
| 273 } | 271 } |
| OLD | NEW |