1ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvistpackage com.android.hotspot2.omadm; 2ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist 3ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvistimport java.util.ArrayList; 4ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvistimport java.util.Collection; 5ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvistimport java.util.Iterator; 6ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvistimport java.util.LinkedHashMap; 7ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvistimport java.util.List; 8ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvistimport java.util.Map; 9ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist 10ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvistpublic class MultiValueMap<T> { 11ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist private final Map<String, ArrayList<T>> mMap = new LinkedHashMap<>(); 12ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist 13ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist public void put(String key, T value) { 14ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist key = key.toLowerCase(); 15ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist ArrayList<T> values = mMap.get(key); 16ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist if (values == null) { 17ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist values = new ArrayList<>(); 18ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist mMap.put(key, values); 19ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 20ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist values.add(value); 21ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 22ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist 23ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist public T get(String key) { 24ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist key = key.toLowerCase(); 25ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist List<T> values = mMap.get(key); 26ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist if (values == null) { 27ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist return null; 28ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } else if (values.size() == 1) { 29ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist return values.get(0); 30ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } else { 31ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist throw new IllegalArgumentException("Cannot do get on multi-value"); 32ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 33ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 34ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist 35ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist public T replace(String key, T oldValue, T newValue) { 36ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist key = key.toLowerCase(); 37ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist List<T> values = mMap.get(key); 38ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist if (values == null) { 39ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist return null; 40ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 41ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist 42ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist for (int n = 0; n < values.size(); n++) { 43ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist T value = values.get(n); 44ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist if (value == oldValue) { 45ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist values.set(n, newValue); 46ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist return value; 47ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 48ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 49ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist return null; 50ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 51ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist 52ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist public T remove(String key, T value) { 53ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist key = key.toLowerCase(); 54ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist List<T> values = mMap.get(key); 55ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist if (values == null) { 56ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist return null; 57ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 58ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist 59ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist T result = null; 60ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist Iterator<T> valueIterator = values.iterator(); 61ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist while (valueIterator.hasNext()) { 62ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist if (valueIterator.next() == value) { 63ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist valueIterator.remove(); 64ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist result = value; 65ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist break; 66ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 67ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 68ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist if (values.isEmpty()) { 69ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist mMap.remove(key); 70ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 71ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist return result; 72ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 73ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist 74ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist public T remove(T value) { 75ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist T result = null; 76ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist Iterator<Map.Entry<String, ArrayList<T>>> iterator = mMap.entrySet().iterator(); 77ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist while (iterator.hasNext()) { 78ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist ArrayList<T> values = iterator.next().getValue(); 79ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist Iterator<T> valueIterator = values.iterator(); 80ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist while (valueIterator.hasNext()) { 81ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist if (valueIterator.next() == value) { 82ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist valueIterator.remove(); 83ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist result = value; 84ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist break; 85ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 86ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 87ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist if (result != null) { 88ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist if (values.isEmpty()) { 89ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist iterator.remove(); 90ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 91ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist break; 92ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 93ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 94ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist return result; 95ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 96ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist 97ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist public Collection<T> values() { 98ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist List<T> allValues = new ArrayList<>(mMap.size()); 99ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist for (List<T> values : mMap.values()) { 100ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist for (T value : values) { 101ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist allValues.add(value); 102ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 103ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 104ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist return allValues; 105ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 106ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist 107ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist public T getSingletonValue() { 108ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist if (mMap.size() != 1) { 109ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist throw new IllegalArgumentException("Map is not a single entry map"); 110ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 111ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist List<T> values = mMap.values().iterator().next(); 112ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist if (values.size() != 1) { 113ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist throw new IllegalArgumentException("Map is not a single entry map"); 114ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 115ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist return values.iterator().next(); 116ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist } 117ee699a61a5687d7c8518b639a940c8e9d1b384ddJan Nordqvist} 118