Skip to content

Commit a2ebecb

Browse files
authored
Merge branch 'master' into dougqh/stats-collapsed-spans-telemetry
2 parents a413f5c + 354f3ab commit a2ebecb

3 files changed

Lines changed: 49 additions & 6 deletions

File tree

‎internal-api/src/main/java/datadog/trace/util/HashingUtils.java‎

Lines changed: 17 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,8 @@
11
package datadog.trace.util;
22

3+
import javax.annotation.Nonnull;
4+
import javax.annotation.Nullable;
5+
36
/**
47
* This class is intended to be a drop-in replacement for the hashing portions of java.util.Objects.
58
* This class provides more convenience methods for hashing primitives and includes overrides for
@@ -8,7 +11,7 @@
811
public final class HashingUtils {
912
private HashingUtils() {}
1013

11-
public static final int hashCode(Object obj) {
14+
public static final int hashCode(@Nullable Object obj) {
1215
return obj != null ? obj.hashCode() : 0;
1316
}
1417

@@ -102,7 +105,7 @@ public static final int addToHash(int hash, int value) {
102105
return 31 * hash + value;
103106
}
104107

105-
public static final int addToHash(int hash, Object obj) {
108+
public static final int addToHash(int hash, @Nullable Object obj) {
106109
return addToHash(hash, hashCode(obj));
107110
}
108111

@@ -134,6 +137,18 @@ public static final int addToHash(int hash, double value) {
134137
return addToHash(hash, Double.hashCode(value));
135138
}
136139

140+
/** Folds {@code arr[0..len)}; the array must be non-null, but its elements may be null. */
141+
public static final int addToHash(int hash, @Nonnull Object[] arr, int len) {
142+
for (int i = 0; i < len; i++) {
143+
hash = addToHash(hash, arr[i]);
144+
}
145+
return hash;
146+
}
147+
148+
public static final int addToHash(int hash, @Nonnull Object[] arr) {
149+
return addToHash(hash, arr, arr.length);
150+
}
151+
137152
public static final int hash(Iterable<?> objs) {
138153
int result = 0;
139154
for (Object obj : objs) {

‎internal-api/src/main/java/datadog/trace/util/LongHashingUtils.java‎

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,8 @@
11
package datadog.trace.util;
22

3+
import javax.annotation.Nonnull;
4+
import javax.annotation.Nullable;
5+
36
/**
47
* This class is intended to be a drop-in replacement for the hashing portions of java.util.Objects.
58
* This class provides more convenience methods for hashing primitives and includes overrides for
@@ -52,7 +55,7 @@ static final long hash(int hash0, int hash1) {
5255
return 31L * hash0 + hash1;
5356
}
5457

55-
private static final int intHash(Object obj) {
58+
private static final int intHash(@Nullable Object obj) {
5659
return obj == null ? 0 : obj.hashCode();
5760
}
5861

@@ -106,7 +109,7 @@ public static final long addToHash(long hash, int value) {
106109
return 31L * hash + value;
107110
}
108111

109-
public static final long addToHash(long hash, Object obj) {
112+
public static final long addToHash(long hash, @Nullable Object obj) {
110113
return addToHash(hash, intHash(obj));
111114
}
112115

@@ -138,14 +141,15 @@ public static final long addToHash(long hash, double value) {
138141
return addToHash(hash, Double.hashCode(value));
139142
}
140143

141-
public static final long addToHash(long hash, Object[] arr, int len) {
144+
/** Folds {@code arr[0..len)}; the array must be non-null, but its elements may be null. */
145+
public static final long addToHash(long hash, @Nonnull Object[] arr, int len) {
142146
for (int i = 0; i < len; i++) {
143147
hash = addToHash(hash, arr[i]);
144148
}
145149
return hash;
146150
}
147151

148-
public static final long addToHash(long hash, Object[] arr) {
152+
public static final long addToHash(long hash, @Nonnull Object[] arr) {
149153
return addToHash(hash, arr, arr.length);
150154
}
151155

‎internal-api/src/test/java/datadog/trace/util/HashingUtilsTest.java‎

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -143,6 +143,30 @@ public void hashArrayAndIterable() {
143143
assertEquals(hashArray, hashIterable);
144144
}
145145

146+
@Test
147+
public void addToHashArrayFoldsFromSeedLikeChainedAddToHash() {
148+
Object[] array = new Object[] {"foo", "bar", "quux"};
149+
150+
// Full-array overload folds every element onto the seed; from zero it matches hash(Object[]).
151+
assertEquals(HashingUtils.hash(array), HashingUtils.addToHash(0, array));
152+
153+
// A non-zero seed carries through, so the result differs from the zero-seed fold.
154+
assertNotEquals(HashingUtils.addToHash(0, array), HashingUtils.addToHash(1, array));
155+
}
156+
157+
@Test
158+
public void addToHashArrayRespectsLen() {
159+
Object[] array = new Object[] {"foo", "bar", "quux"};
160+
161+
// The len override folds only the first len elements.
162+
assertEquals(
163+
HashingUtils.hash(new Object[] {"foo", "bar"}), HashingUtils.addToHash(0, array, 2));
164+
assertNotEquals(HashingUtils.addToHash(0, array), HashingUtils.addToHash(0, array, 2));
165+
166+
// len==0 never enters the loop and returns the seed unchanged.
167+
assertEquals(42, HashingUtils.addToHash(42, array, 0));
168+
}
169+
146170
@ParameterizedTest
147171
@ValueSource(booleans = {false, true})
148172
public void booleans(boolean value) {

0 commit comments

Comments
 (0)