-
Notifications
You must be signed in to change notification settings - Fork 966
Expand file tree
/
Copy pathDictionaryTable.java
More file actions
60 lines (54 loc) · 1.99 KB
/
DictionaryTable.java
File metadata and controls
60 lines (54 loc) · 1.99 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
/*
* Copyright The OpenTelemetry Authors
* SPDX-License-Identifier: Apache-2.0
*/
package io.opentelemetry.sdk.profiles;
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
/**
* This data structure is effectively an indexed Set.
*
* <p>It stores each offered element without duplication (like a Set, not a List), but supports
* reference to elements by their position (like a List index).
*
* <p>This class is not threadsafe and must be externally synchronized.
*
* <p>For a given Object o, after i = putIfAbsent(o), then getTable().get(i).equals(o);
*
* @param <T> the type of elements maintained by this table. The type should implement equals and
* hashCode in a manner consistent with Set/Map key expectations.
*/
public class DictionaryTable<T> {
// Whilst it's possible to compute either from the other, we keep two views on the data,
// prioritising access efficiency over memory footprint.
private final List<T> table = new ArrayList<>();
private final Map<T, Integer> map = new HashMap<>();
/**
* Stores the provided element if an equivalent is not already present, and returns its index.
*
* <p>Note that whilst the update semantics of this method are consistent with Map.putIfAbsent,
* the return value is always the index, i.e. reflects the post-update state, not the prior state,
* and therefore does not allow for determining if the method had an effect or not.
*
* @param value an element to store.
* @return the index of the added or existing element.
*/
public Integer putIfAbsent(T value) {
Integer index = map.computeIfAbsent(value, k -> map.size());
if (map.size() != table.size()) {
table.add(value);
}
return index;
}
/**
* Provides a view of the Table in List form.
*
* @return an immutable List containing the table entries in index position.
*/
public List<T> getTable() {
return Collections.unmodifiableList(table);
}
}