001/* 002 * Copyright (C) 2009 The Guava Authors 003 * 004 * Licensed under the Apache License, Version 2.0 (the "License"); 005 * you may not use this file except in compliance with the License. 006 * You may obtain a copy of the License at 007 * 008 * http://www.apache.org/licenses/LICENSE-2.0 009 * 010 * Unless required by applicable law or agreed to in writing, software 011 * distributed under the License is distributed on an "AS IS" BASIS, 012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013 * See the License for the specific language governing permissions and 014 * limitations under the License. 015 */ 016 017package com.google.common.collect.testing.google; 018 019import static com.google.common.base.Preconditions.checkNotNull; 020import static com.google.common.collect.Iterables.getOnlyElement; 021import static com.google.common.collect.Maps.immutableEnumMap; 022import static com.google.common.collect.testing.Helpers.mapEntry; 023import static java.util.Arrays.asList; 024 025import com.google.common.annotations.GwtCompatible; 026import com.google.common.collect.ImmutableMap; 027import com.google.common.collect.ImmutableSet; 028import com.google.common.collect.Ordering; 029import com.google.common.collect.testing.AnEnum; 030import com.google.common.collect.testing.SampleElements; 031import com.google.common.collect.testing.TestEnumMapGenerator; 032import com.google.common.collect.testing.TestListGenerator; 033import com.google.common.collect.testing.TestMapGenerator; 034import com.google.common.collect.testing.TestStringListGenerator; 035import com.google.common.collect.testing.TestStringMapGenerator; 036import com.google.common.collect.testing.TestUnhashableCollectionGenerator; 037import com.google.common.collect.testing.UnhashableObject; 038import java.util.Collection; 039import java.util.EnumMap; 040import java.util.HashMap; 041import java.util.LinkedHashMap; 042import java.util.List; 043import java.util.Map; 044import java.util.Map.Entry; 045import org.jspecify.annotations.NullMarked; 046 047/** 048 * Generators of different types of map and related collections, such as keys, entries and values. 049 * 050 * @author Hayward Chan 051 */ 052@GwtCompatible 053@NullMarked 054public class MapGenerators { 055 public static class ImmutableMapGenerator extends TestStringMapGenerator { 056 @Override 057 protected Map<String, String> create(Entry<String, String>[] entries) { 058 ImmutableMap.Builder<String, String> builder = ImmutableMap.builder(); 059 for (Entry<String, String> entry : entries) { 060 checkNotNull(entry); 061 builder.put(entry.getKey(), entry.getValue()); 062 } 063 return builder.buildOrThrow(); 064 } 065 } 066 067 public static class ImmutableMapCopyOfGenerator extends TestStringMapGenerator { 068 @Override 069 protected Map<String, String> create(Entry<String, String>[] entries) { 070 Map<String, String> builder = new LinkedHashMap<>(); 071 for (Entry<String, String> entry : entries) { 072 builder.put(entry.getKey(), entry.getValue()); 073 } 074 return ImmutableMap.copyOf(builder); 075 } 076 } 077 078 public static class ImmutableMapCopyOfEntriesGenerator extends TestStringMapGenerator { 079 @Override 080 protected Map<String, String> create(Entry<String, String>[] entries) { 081 return ImmutableMap.copyOf(asList(entries)); 082 } 083 } 084 085 public static class ImmutableMapUnhashableValuesGenerator 086 extends TestUnhashableCollectionGenerator<Collection<UnhashableObject>> { 087 088 @Override 089 public Collection<UnhashableObject> create(UnhashableObject[] elements) { 090 ImmutableMap.Builder<Integer, UnhashableObject> builder = ImmutableMap.builder(); 091 int key = 1; 092 for (UnhashableObject value : elements) { 093 builder.put(key++, value); 094 } 095 return builder.buildOrThrow().values(); 096 } 097 } 098 099 public static class ImmutableMapKeyListGenerator extends TestStringListGenerator { 100 @Override 101 public List<String> create(String[] elements) { 102 ImmutableMap.Builder<String, Integer> builder = ImmutableMap.builder(); 103 for (int i = 0; i < elements.length; i++) { 104 builder.put(elements[i], i); 105 } 106 return builder.buildOrThrow().keySet().asList(); 107 } 108 } 109 110 public static class ImmutableMapValueListGenerator extends TestStringListGenerator { 111 @Override 112 public List<String> create(String[] elements) { 113 ImmutableMap.Builder<Integer, String> builder = ImmutableMap.builder(); 114 for (int i = 0; i < elements.length; i++) { 115 builder.put(i, elements[i]); 116 } 117 return builder.buildOrThrow().values().asList(); 118 } 119 } 120 121 public static class ImmutableMapEntryListGenerator 122 implements TestListGenerator<Entry<String, Integer>> { 123 124 @Override 125 public SampleElements<Entry<String, Integer>> samples() { 126 return new SampleElements<>( 127 mapEntry("foo", 5), 128 mapEntry("bar", 3), 129 mapEntry("baz", 17), 130 mapEntry("quux", 1), 131 mapEntry("toaster", -2)); 132 } 133 134 @SuppressWarnings("unchecked") 135 @Override 136 public Entry<String, Integer>[] createArray(int length) { 137 return (Entry<String, Integer>[]) new Entry<?, ?>[length]; 138 } 139 140 @Override 141 public Iterable<Entry<String, Integer>> order(List<Entry<String, Integer>> insertionOrder) { 142 return insertionOrder; 143 } 144 145 @Override 146 public List<Entry<String, Integer>> create(Object... elements) { 147 ImmutableMap.Builder<String, Integer> builder = ImmutableMap.builder(); 148 for (Object o : elements) { 149 @SuppressWarnings("unchecked") 150 Entry<String, Integer> entry = (Entry<String, Integer>) checkNotNull(o); 151 builder.put(entry); 152 } 153 return builder.buildOrThrow().entrySet().asList(); 154 } 155 } 156 157 public static class ImmutableEnumMapGenerator extends TestEnumMapGenerator { 158 @Override 159 protected Map<AnEnum, String> create(Entry<AnEnum, String>[] entries) { 160 Map<AnEnum, String> map = new HashMap<>(); 161 for (Entry<AnEnum, String> entry : entries) { 162 checkNotNull(entry); 163 map.put(entry.getKey(), entry.getValue()); 164 } 165 return immutableEnumMap(map); 166 } 167 } 168 169 public static class ImmutableMapCopyOfEnumMapGenerator extends TestEnumMapGenerator { 170 @Override 171 protected Map<AnEnum, String> create(Entry<AnEnum, String>[] entries) { 172 EnumMap<AnEnum, String> map = new EnumMap<>(AnEnum.class); 173 for (Entry<AnEnum, String> entry : entries) { 174 map.put(entry.getKey(), entry.getValue()); 175 } 176 return ImmutableMap.copyOf(map); 177 } 178 179 @Override 180 public Iterable<Entry<AnEnum, String>> order(List<Entry<AnEnum, String>> insertionOrder) { 181 return new Ordering<Entry<AnEnum, String>>() { 182 183 @Override 184 public int compare(Entry<AnEnum, String> left, Entry<AnEnum, String> right) { 185 return left.getKey().compareTo(right.getKey()); 186 } 187 }.sortedCopy(insertionOrder); 188 } 189 } 190 191 public static class ImmutableMapValuesAsSingletonSetGenerator 192 implements TestMapGenerator<String, Collection<Integer>> { 193 194 @Override 195 public SampleElements<Entry<String, Collection<Integer>>> samples() { 196 return new SampleElements<>( 197 mapEntry("one", ImmutableSet.of(10000)), 198 mapEntry("two", ImmutableSet.of(-2000)), 199 mapEntry("three", ImmutableSet.of(300)), 200 mapEntry("four", ImmutableSet.of(-40)), 201 mapEntry("five", ImmutableSet.of(5))); 202 } 203 204 @Override 205 public Map<String, Collection<Integer>> create(Object... elements) { 206 ImmutableMap.Builder<String, Integer> builder = ImmutableMap.builder(); 207 // assumes that each set is a singleton or less (as is done for the samples) 208 for (Object elem : elements) { 209 @SuppressWarnings("unchecked") // safe by generator contract 210 Entry<String, Collection<Integer>> entry = (Entry<String, Collection<Integer>>) elem; 211 Integer value = getOnlyElement(entry.getValue()); 212 builder.put(entry.getKey(), value); 213 } 214 return builder.buildOrThrow().asMultimap().asMap(); 215 } 216 217 @Override 218 @SuppressWarnings({"unchecked", "rawtypes"}) // needed for arrays 219 public Entry<String, Collection<Integer>>[] createArray(int length) { 220 return new Entry[length]; 221 } 222 223 @Override 224 public Iterable<Entry<String, Collection<Integer>>> order( 225 List<Entry<String, Collection<Integer>>> insertionOrder) { 226 return insertionOrder; 227 } 228 229 @Override 230 public String[] createKeyArray(int length) { 231 return new String[length]; 232 } 233 234 @Override 235 @SuppressWarnings({"unchecked", "rawtypes"}) // needed for arrays 236 public Collection<Integer>[] createValueArray(int length) { 237 return new ImmutableSet[length]; 238 } 239 } 240 241 /** 242 * Useless constructor for a class of static utility methods. 243 * 244 * @deprecated Do not instantiate this utility class. 245 */ 246 @Deprecated 247 public MapGenerators() {} 248}