001/* 002 * Licensed to the Apache Software Foundation (ASF) under one or more 003 * contributor license agreements. See the NOTICE file distributed with 004 * this work for additional information regarding copyright ownership. 005 * The ASF licenses this file to You under the Apache License, Version 2.0 006 * (the "License"); you may not use this file except in compliance with 007 * the License. You may obtain a copy of the License at 008 * 009 * http://www.apache.org/licenses/LICENSE-2.0 010 * 011 * Unless required by applicable law or agreed to in writing, software 012 * distributed under the License is distributed on an "AS IS" BASIS, 013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 014 * See the License for the specific language governing permissions and 015 * limitations under the License. 016 */ 017package org.apache.juneau.internal; 018 019import static org.apache.juneau.internal.ArrayUtils.*; 020 021import java.lang.reflect.*; 022import java.util.*; 023 024import org.apache.juneau.common.utils.*; 025 026/** 027 * An instance of a <c>Map</c> where the keys and values are simple arrays. 028 * 029 * <p> 030 * Typically more efficient than <c>HashMaps</c> for small maps (e.g. <10 entries). 031 * 032 * <p> 033 * Does not support adding or removing entries. 034 * 035 * <p> 036 * Setting values overwrites the value on the underlying value array. 037 * 038 * <h5 class='section'>See Also:</h5><ul> 039 040 * </ul> 041 * 042 * @param <K> The key type. 043 * @param <V> The value type. 044 */ 045public class SimpleMap<K,V> extends AbstractMap<K,V> { 046 047 final K[] keys; 048 final V[] values; 049 final SimpleMapEntry[] entries; 050 051 /** 052 * Constructor. 053 * 054 * @param keys The map keys. Must not be <jk>null</jk>. 055 * @param values The map values. Must not be <jk>null</jk>. 056 */ 057 @SuppressWarnings("unchecked") 058 public SimpleMap(K[] keys, V[] values) { 059 Utils.assertArgNotNull("keys", keys); 060 Utils.assertArgNotNull("values", values); 061 Utils.assertArg(keys.length == values.length, "keys ''{0}'' and values ''{1}'' array lengths differ", keys.length, values.length); 062 063 this.keys = keys; 064 this.values = values; 065 entries = (SimpleMapEntry[]) Array.newInstance(SimpleMapEntry.class, keys.length); 066 for (int i = 0; i < keys.length; i++) { 067 Utils.assertArg(keys[i] != null, "Keys array cannot contain a null value."); 068 entries[i] = new SimpleMapEntry(i); 069 } 070 } 071 072 @Override /* Map */ 073 public Set<Map.Entry<K,V>> entrySet() { 074 return asSet(entries); 075 } 076 077 @Override /* Map */ 078 public V get(Object key) { 079 for (int i = 0; i < keys.length; i++) 080 if (keys[i].equals(key)) 081 return values[i]; 082 return null; 083 } 084 085 @Override /* Map */ 086 public Set<K> keySet() { 087 return asSet(keys); 088 } 089 090 @Override /* Map */ 091 public V put(K key, V value) { 092 for (int i = 0; i < keys.length; i++) { 093 if (keys[i].equals(key)) { 094 V v = values[i]; 095 values[i] = value; 096 return v; 097 } 098 } 099 throw new IllegalArgumentException("No key '"+key+"' defined in map"); 100 } 101 102 class SimpleMapEntry implements Map.Entry<K,V> { 103 104 private int index; 105 106 SimpleMapEntry(int index) { 107 this.index = index; 108 } 109 110 @Override /* Map.Entry */ 111 public K getKey() { 112 return keys[index]; 113 } 114 115 @Override /* Map.Entry */ 116 public V getValue() { 117 return values[index]; 118 } 119 120 @Override /* Map.Entry */ 121 public V setValue(V val) { 122 V v = values[index]; 123 values[index] = val; 124 return v; 125 } 126 } 127}