1 16 package org.springframework.binding.collection; 17 18 import java.util.Collection ; 19 import java.util.Iterator ; 20 import java.util.Map ; 21 import java.util.NoSuchElementException ; 22 import java.util.Set ; 23 24 30 public abstract class StringKeyedMapAdapter implements Map { 31 32 private Set keySet; 33 34 private Collection values; 35 36 private Set entrySet; 37 38 40 public void clear() { 41 for (Iterator it = getAttributeNames(); it.hasNext();) { 42 removeAttribute((String )it.next()); 43 } 44 } 45 46 public boolean containsKey(Object key) { 47 return getAttribute(key.toString()) != null; 48 } 49 50 public boolean containsValue(Object value) { 51 if (value == null) { 52 return false; 53 } 54 for (Iterator it = getAttributeNames(); it.hasNext();) { 55 Object aValue = getAttribute((String )it.next()); 56 if (value.equals(aValue)) { 57 return true; 58 } 59 } 60 return false; 61 } 62 63 public Set entrySet() { 64 return (entrySet != null) ? entrySet : (entrySet = new EntrySet()); 65 } 66 67 public Object get(Object key) { 68 return getAttribute(key.toString()); 69 } 70 71 public boolean isEmpty() { 72 return !getAttributeNames().hasNext(); 73 } 74 75 public Set keySet() { 76 return (keySet != null) ? keySet : (keySet = new KeySet()); 77 } 78 79 public Object put(Object key, Object value) { 80 String stringKey = String.valueOf(key); 81 Object previousValue = getAttribute(stringKey); 82 setAttribute(stringKey, value); 83 return previousValue; 84 } 85 86 public void putAll(Map map) { 87 for (Iterator it = map.entrySet().iterator(); it.hasNext();) { 88 Entry entry = (Entry)it.next(); 89 setAttribute(entry.getKey().toString(), entry.getValue()); 90 } 91 } 92 93 public Object remove(Object key) { 94 String stringKey = key.toString(); 95 Object retval = getAttribute(stringKey); 96 removeAttribute(stringKey); 97 return retval; 98 } 99 100 public int size() { 101 int size = 0; 102 for (Iterator it = getAttributeNames(); it.hasNext();) { 103 size++; 104 it.next(); 105 } 106 return size; 107 } 108 109 public Collection values() { 110 return (values != null) ? values : (values = new Values()); 111 } 112 113 115 121 protected abstract Object getAttribute(String key); 122 123 130 protected abstract void setAttribute(String key, Object value); 131 132 137 protected abstract void removeAttribute(String key); 138 139 144 protected abstract Iterator getAttributeNames(); 145 146 148 private abstract class AbstractSet extends java.util.AbstractSet { 149 public boolean isEmpty() { 150 return StringKeyedMapAdapter.this.isEmpty(); 151 } 152 153 public int size() { 154 return StringKeyedMapAdapter.this.size(); 155 } 156 157 public void clear() { 158 StringKeyedMapAdapter.this.clear(); 159 } 160 } 161 162 private class KeySet extends AbstractSet { 163 public Iterator iterator() { 164 return new KeyIterator(); 165 } 166 167 public boolean contains(Object o) { 168 return StringKeyedMapAdapter.this.containsKey(o); 169 } 170 171 public boolean remove(Object o) { 172 return StringKeyedMapAdapter.this.remove(o) != null; 173 } 174 } 175 176 private class KeyIterator implements Iterator { 177 protected final Iterator it = getAttributeNames(); 178 179 protected Object currentKey; 180 181 public void remove() { 182 if (currentKey == null) { 183 throw new NoSuchElementException ("You must call next() at least once"); 184 } 185 StringKeyedMapAdapter.this.remove(currentKey); 186 } 187 188 public boolean hasNext() { 189 return it.hasNext(); 190 } 191 192 public Object next() { 193 return currentKey = it.next(); 194 } 195 } 196 197 private class Values extends AbstractSet { 198 public Iterator iterator() { 199 return new ValuesIterator(); 200 } 201 202 public boolean contains(Object o) { 203 return StringKeyedMapAdapter.this.containsValue(o); 204 } 205 206 public boolean remove(Object o) { 207 if (o == null) { 208 return false; 209 } 210 for (Iterator it = iterator(); it.hasNext();) { 211 if (o.equals(it.next())) { 212 it.remove(); 213 return true; 214 } 215 } 216 return false; 217 } 218 } 219 220 private class ValuesIterator extends KeyIterator { 221 public Object next() { 222 super.next(); 223 return StringKeyedMapAdapter.this.get(currentKey); 224 } 225 } 226 227 private class EntrySet extends AbstractSet { 228 public Iterator iterator() { 229 return new EntryIterator(); 230 } 231 232 public boolean contains(Object o) { 233 if (!(o instanceof Entry)) { 234 return false; 235 } 236 Entry entry = (Entry)o; 237 Object key = entry.getKey(); 238 Object value = entry.getValue(); 239 if (key == null || value == null) { 240 return false; 241 } 242 return value.equals(StringKeyedMapAdapter.this.get(key)); 243 } 244 245 public boolean remove(Object o) { 246 if (!(o instanceof Entry)) { 247 return false; 248 } 249 Entry entry = (Entry)o; 250 Object key = entry.getKey(); 251 Object value = entry.getValue(); 252 if (key == null || value == null || !value.equals(StringKeyedMapAdapter.this.get(key))) { 253 return false; 254 } 255 return StringKeyedMapAdapter.this.remove(((Entry)o).getKey()) != null; 256 } 257 } 258 259 private class EntryIterator extends KeyIterator { 260 public Object next() { 261 super.next(); 262 return new EntrySetEntry(currentKey); 263 } 264 } 265 266 private class EntrySetEntry implements Entry { 267 private final Object currentKey; 268 269 public EntrySetEntry(Object currentKey) { 270 this.currentKey = currentKey; 271 } 272 273 public Object getKey() { 274 return currentKey; 275 } 276 277 public Object getValue() { 278 return StringKeyedMapAdapter.this.get(currentKey); 279 } 280 281 public Object setValue(Object value) { 282 return StringKeyedMapAdapter.this.put(currentKey, value); 283 } 284 } 285 } | Popular Tags |