|
Author: doogie
Date: Sun Nov 29 21:26:37 2009 New Revision: 885275 URL: http://svn.apache.org/viewvc?rev=885275&view=rev Log: UtilCache is now a map. keySet, entrySet, and values iterators won't reflect items added/removed. However, most membership tests directly access the underlying cache anyways, so this isn't a big deal. Added: ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMap.java ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapCollection.java ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapEntry.java ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapEntrySet.java ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapKeySet.java ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapSet.java ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapValues.java ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/IteratorWrapper.java ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/ReadOnlyMapEntry.java Modified: ofbiz/trunk/framework/base/src/org/ofbiz/base/util/cache/CacheLineTable.java ofbiz/trunk/framework/base/src/org/ofbiz/base/util/cache/UtilCache.java Modified: ofbiz/trunk/framework/base/src/org/ofbiz/base/util/cache/CacheLineTable.java URL: http://svn.apache.org/viewvc/ofbiz/trunk/framework/base/src/org/ofbiz/base/util/cache/CacheLineTable.java?rev=885275&r1=885274&r2=885275&view=diff ============================================================================== --- ofbiz/trunk/framework/base/src/org/ofbiz/base/util/cache/CacheLineTable.java (original) +++ ofbiz/trunk/framework/base/src/org/ofbiz/base/util/cache/CacheLineTable.java Sun Nov 29 21:26:37 2009 @@ -23,6 +23,7 @@ import java.util.Collection; import java.util.Collections; import java.util.HashSet; +import java.util.Iterator; import java.util.List; import java.util.Map; import java.util.Set; @@ -34,6 +35,7 @@ import org.ofbiz.base.util.ObjectType; import org.ofbiz.base.util.UtilValidate; import org.ofbiz.base.util.collections.LRUMap; +import org.ofbiz.base.util.collections.ReadOnlyMapEntry; @SuppressWarnings("serial") public class CacheLineTable<K, V> implements Serializable { @@ -212,6 +214,35 @@ return values; } + public synchronized Iterator<Map.Entry<K, ? extends CacheLine<V>>> iterator() { + // this is a list, instead of a set, as the fileTable or + // memoryTable has already deduped keys for us, and this ends up + // being faster, as the hashCode/equals calls don't need to happen + List<Map.Entry<K, ? extends CacheLine<V>>> list = FastList.newInstance(); + if (fileTable != null) { + try { + jdbm.helper.FastIterator iter = fileTable.keys(); + Object key = iter.next(); + while (key != null) { + CacheLine<V> value = (CacheLine<V>) fileTable.get(key); + if (key instanceof ObjectType.NullObject) { + key = null; + } + list.add(new ReadOnlyMapEntry<K, CacheLine<V>>((K) key, value)); + key = iter.next(); + } + } catch (IOException e) { + Debug.logError(e, module); + } + } else { + list.addAll(memoryTable.entrySet()); + if (isNullSet) { + list.add(new ReadOnlyMapEntry<K, CacheLine<V>>(null, nullValue)); + } + } + return list.iterator(); + } + /** * * @return An unmodifiable Set for the keys for this cache; to remove while iterating call the remove method on this class. Modified: ofbiz/trunk/framework/base/src/org/ofbiz/base/util/cache/UtilCache.java URL: http://svn.apache.org/viewvc/ofbiz/trunk/framework/base/src/org/ofbiz/base/util/cache/UtilCache.java?rev=885275&r1=885274&r2=885275&view=diff ============================================================================== --- ofbiz/trunk/framework/base/src/org/ofbiz/base/util/cache/UtilCache.java (original) +++ ofbiz/trunk/framework/base/src/org/ofbiz/base/util/cache/UtilCache.java Sun Nov 29 21:26:37 2009 @@ -21,8 +21,8 @@ import java.io.Serializable; import java.util.ArrayList; import java.util.Collection; -import java.util.Collections; import java.util.HashSet; +import java.util.Iterator; import java.util.List; import java.util.Map; import java.util.MissingResourceException; @@ -37,6 +37,9 @@ import org.ofbiz.base.util.Debug; import org.ofbiz.base.util.UtilValidate; +import org.ofbiz.base.util.collections.GenericMap; +import org.ofbiz.base.util.collections.GenericMapEntry; +import org.ofbiz.base.util.collections.IteratorWrapper; /** * Generalized caching utility. Provides a number of caching features: @@ -50,7 +53,7 @@ * */ @SuppressWarnings("serial") -public class UtilCache<K, V> implements Serializable { +public class UtilCache<K, V> extends GenericMap<K, V> implements Serializable { public static final String module = UtilCache.class.getName(); @@ -222,6 +225,41 @@ return cacheLineTable.isEmpty(); } + protected Iterator<Map.Entry<K, V>> iterator(final boolean noteAccess) { + return new IteratorWrapper<Map.Entry<K, V>, Map.Entry<K, ? extends CacheLine<V>>>(cacheLineTable.iterator()) { + protected Map.Entry<K, V> convert(Map.Entry<K, ? extends CacheLine<V>> src) { + return new GenericMapEntry<K, V>(UtilCache.this, src.getKey(), noteAccess); + } + + protected void noteRemoval(Map.Entry<K, V> dest, Map.Entry<K, ? extends CacheLine<V>> src) { + UtilCache.this.remove(dest.getKey()); + } + }; + } + + protected <KE extends K, VE extends V> void putAll(Iterator<Map.Entry<KE, VE>> it) { + long accessTime = System.currentTimeMillis(); + while (it.hasNext()) { + Map.Entry<KE, VE> entry = it.next(); + K key = entry.getKey(); + V value = entry.getValue(); + CacheLine<V> oldCacheLine; + CacheLine<V> newCacheLine; + if (expireTime > 0) { + newCacheLine = useSoftReference ? new SoftRefCacheLine<V>(value, accessTime, expireTime) : new HardRefCacheLine<V>(value, accessTime, expireTime); + } else { + newCacheLine = useSoftReference ? new SoftRefCacheLine<V>(value, expireTime) : new HardRefCacheLine<V>(value, expireTime); + } + oldCacheLine = cacheLineTable.put(key, newCacheLine); + + if (oldCacheLine == null) { + noteAddition(key, value); + } else { + noteUpdate(key, value, oldCacheLine.getValue()); + } + } + } + /** Puts or loads the passed element into the cache * @param key The key for the element, used to reference it in the hastables and LRU linked list * @param value The value of the element @@ -260,8 +298,8 @@ * @param key The key for the element, used to reference it in the hastables and LRU linked list * @return The value of the element specified by the key */ - public V get(Object key) { - CacheLine<V> line = getInternal(key, true); + protected V get(Object key, boolean noteAccess) { + CacheLine<V> line = getInternal(key, noteAccess); if (line == null) { return null; } else { @@ -294,19 +332,6 @@ return line; } - public Collection<V> values() { - if (cacheLineTable.isEmpty()) { - return Collections.emptyList(); - } - - List<V> valuesList = FastList.newInstance(); - for (K key: cacheLineTable.keySet()) { - valuesList.add(this.get(key)); - } - - return valuesList; - } - public long getSizeInBytes() { long totalSize = 0; for (CacheLine<V> line: cacheLineTable.values()) { @@ -535,7 +560,7 @@ * This behavior is necessary for now for the persisted cache feature. */ public Set<? extends K> getCacheLineKeys() { - return cacheLineTable.keySet(); + return keySet(); } public Collection<? extends CacheLine<V>> getCacheLineValues() { Added: ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMap.java URL: http://svn.apache.org/viewvc/ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMap.java?rev=885275&view=auto ============================================================================== --- ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMap.java (added) +++ ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMap.java Sun Nov 29 21:26:37 2009 @@ -0,0 +1,190 @@ +/*******n*********************************************************************** + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + *******************************************************************************/ +package org.ofbiz.base.util.collections; + +import java.io.Serializable; +import java.util.Collection; +import java.util.Iterator; +import java.util.Map; +import java.util.Set; +import java.util.concurrent.atomic.AtomicReferenceFieldUpdater; + +import org.ofbiz.base.util.Appender; +import org.ofbiz.base.util.UtilGenerics; +import org.ofbiz.base.util.UtilObject; + +public abstract class GenericMap<K, V> implements Appender<StringBuilder>, Map<K, V>, Serializable { + private static final AtomicReferenceFieldUpdater<GenericMap, Set> keySetUpdater = AtomicReferenceFieldUpdater.newUpdater(GenericMap.class, Set.class, "keySet"); + private static final AtomicReferenceFieldUpdater<GenericMap, Set> entrySetUpdater = AtomicReferenceFieldUpdater.newUpdater(GenericMap.class, Set.class, "entrySet"); + private static final AtomicReferenceFieldUpdater<GenericMap, Collection> valuesUpdater = AtomicReferenceFieldUpdater.newUpdater(GenericMap.class, Collection.class, "values"); + + private volatile Set<K> keySet; + private volatile Set<Map.Entry<K, V>> entrySet; + private volatile Collection<V> values; + + public boolean containsValue(Object value) { + return values().contains(value); + } + + public boolean equals(Object o) { + if (!(o instanceof Map)) return false; + if (this == o) return true; + Map map = (Map) o; + if (size() != map.size()) return false; + if (o instanceof GenericMap) return equalsGenericMap((GenericMap) o); + return equalsMap(map); + } + + protected boolean equalsGenericMap(GenericMap map) { + Iterator<Map.Entry<K, V>> it = iterator(false); + while (it.hasNext()) { + Map.Entry<K, V> entry = it.next(); + K key = entry.getKey(); + V value = entry.getValue(); + if (value != null) { + if (!value.equals(map.get(key, false))) return false; + } else { + Object otherValue = map.get(key, false); + if (otherValue != null) return false; + if (!map.containsKey(key)) return false; + } + } + return true; + } + + protected boolean equalsMap(Map map) { + Iterator<Map.Entry<K, V>> it = iterator(false); + while (it.hasNext()) { + Map.Entry<K, V> entry = it.next(); + K key = entry.getKey(); + V value = entry.getValue(); + if (value != null) { + if (!value.equals(map.get(key))) return false; + } else { + Object otherValue = map.get(key); + if (otherValue != null) return false; + if (!map.containsKey(key)) return false; + } + } + return true; + } + + public final V get(Object key) { + return get(key, true); + } + + protected abstract V get(Object key, boolean noteAccess); + + public final Set<Map.Entry<K, V>> entrySet() { + if (entrySet == null) { + entrySetUpdater.compareAndSet(this, null, new GenericMapEntrySet<K, V, GenericMap<K, V>>(this) { + protected boolean contains(Object key, Object value) { + return UtilObject.equalsHelper(get(key, false), value); + } + + public Iterator<Map.Entry<K, V>> iterator(boolean noteAccess) { + return GenericMap.this.iterator(noteAccess); + } + }); + } + return entrySet; + } + + protected abstract Iterator<Map.Entry<K, V>> iterator(boolean noteAccess); + + public final Set<K> keySet() { + if (keySet == null) { + keySetUpdater.compareAndSet(this, null, new GenericMapKeySet<K, V, GenericMap<K, V>>(this) { + public boolean contains(Object key) { + return containsKey(key); + } + + public Iterator<K> iterator(boolean noteAccess) { + return new IteratorWrapper<K, Map.Entry<K, V>>(GenericMap.this.iterator(noteAccess)) { + protected void noteRemoval(K dest, Map.Entry<K, V> src) { + // No need to note the remove, the wrapped iterator does that for us + // evictionPolicy.remove(evictionDeque, dest); + // if (diskStore != null) diskStore.remove(dest); + } + + protected K convert(Map.Entry<K, V> src) { + return src.getKey(); + } + }; + } + }); + } + return keySet; + } + + public final Collection<V> values() { + if (values == null) { + valuesUpdater.compareAndSet(this, null, new GenericMapValues<K, V, GenericMap<K, V>>(this) { + public Iterator<V> iterator(boolean noteAccess) { + return new IteratorWrapper<V, Map.Entry<K, V>>(GenericMap.this.iterator(noteAccess)) { + protected void noteRemoval(V dest, Map.Entry<K, V> src) { + // No need to note the remove, the wrapped iterator does that for us + // evictionPolicy.remove(evictionDeque, src.getKey()); + // if (diskStore != null) diskStore.remove(src.getKey()); + } + + protected V convert(Map.Entry<K, V> src) { + return src.getValue(); + } + }; + } + }); + } + return values; + } + + public void putAll(Map<? extends K, ? extends V> map) { + putAllInternal(map); + } + + private <KE extends K, VE extends V> void putAllInternal(Map<KE, VE> map) { + Iterator<Map.Entry<KE, VE>> it; + if (map instanceof GenericMap) { + GenericMap<KE, VE> otherMap = UtilGenerics.cast(map); + it = otherMap.iterator(false); + } else { + it = map.entrySet().iterator(); + } + putAll(it); + } + + protected abstract <KE extends K, VE extends V> void putAll(Iterator<Map.Entry<KE, VE>> it); + + public String toString() { + StringBuilder sb = new StringBuilder(); + return appendTo(new StringBuilder()).toString(); + } + + public StringBuilder appendTo(StringBuilder sb) { + sb.append("{"); + Iterator<Map.Entry<K, V>> it = iterator(false); + while (it.hasNext()) { + Map.Entry<K, V> entry = it.next(); + sb.append(entry.getKey()).append("=").append(entry.getValue()); + if (it.hasNext()) sb.append(","); + } + return sb.append("}"); + } +} + Added: ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapCollection.java URL: http://svn.apache.org/viewvc/ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapCollection.java?rev=885275&view=auto ============================================================================== --- ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapCollection.java (added) +++ ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapCollection.java Sun Nov 29 21:26:37 2009 @@ -0,0 +1,124 @@ +/******************************************************************************* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + *******************************************************************************/ +package org.ofbiz.base.util.collections; + +import java.util.Collection; +import java.util.Iterator; +import java.util.List; +import java.util.Map; + +import javolution.util.FastList; + +import org.ofbiz.base.util.Appender; + +public abstract class GenericMapCollection<K, V, M extends Map<K, V>, I> implements Collection<I> { + protected final M source; + + public GenericMapCollection(M source) { + this.source = source; + } + + public boolean add(I item) { + throw new UnsupportedOperationException(); + } + + public boolean addAll(Collection<? extends I> collection) { + throw new UnsupportedOperationException(); + } + + public void clear() { + source.clear(); + } + + public boolean containsAll(Collection<?> collection) { + int count = 0; + for (Object item: collection) { + if (!contains(item)) return false; + } + return true; + } + + public boolean isEmpty() { + return source.isEmpty(); + } + + public final Iterator<I> iterator() { + return iterator(true); + } + + protected abstract Iterator<I> iterator(boolean noteAccess); + + public boolean removeAll(Collection<?> collection) { + int count = 0; + for (Object item: collection) { + if (remove(item)) count++; + } + return count > 0; + } + + public boolean retainAll(Collection<?> collection) { + int count = 0; + Iterator<I> it = iterator(false); + while (it.hasNext()) { + I item = it.next(); + if (!collection.contains(item)) { + it.remove(); + count++; + } + } + return count > 0; + } + + public int size() { + return source.size(); + } + + public Object[] toArray() { + List<I> list = FastList.newInstance(); + Iterator<I> it = iterator(false); + while (it.hasNext()) { + list.add(it.next()); + } + return list.toArray(); + } + + public <T> T[] toArray(T[] array) { + List<Object> list = FastList.newInstance(); + Iterator<I> it = iterator(false); + while (it.hasNext()) { + list.add(it.next()); + } + return list.toArray(array); + } + + public String toString() { + return appendTo(new StringBuilder()).toString(); + } + + public StringBuilder appendTo(StringBuilder sb) { + sb.append("["); + Iterator<I> it = iterator(false); + while (it.hasNext()) { + sb.append(it.next()); + if (it.hasNext()) sb.append(", "); + } + return sb.append("]"); + } +} + Added: ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapEntry.java URL: http://svn.apache.org/viewvc/ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapEntry.java?rev=885275&view=auto ============================================================================== --- ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapEntry.java (added) +++ ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapEntry.java Sun Nov 29 21:26:37 2009 @@ -0,0 +1,58 @@ +/******************************************************************************* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + *******************************************************************************/ +package org.ofbiz.base.util.collections; + +import java.util.Map; + +import org.ofbiz.base.util.UtilObject; + +public class GenericMapEntry<K, V> implements Map.Entry<K, V> { + protected final GenericMap<K, V> map; + protected final K key; + protected final boolean noteAccess; + + public GenericMapEntry(GenericMap<K, V> map, K key, boolean noteAccess) { + this.map = map; + this.key = key; + this.noteAccess = noteAccess; + } + + public K getKey() { + return key; + } + + public V getValue() { + return map.get(key, noteAccess); + } + + public V setValue(V value) { + return map.put(key, value); + } + + public boolean equals(Object o) { + if (!(o instanceof Map.Entry)) return false; + if (this == o) return true; + Map.Entry other = (Map.Entry) o; + return UtilObject.equalsHelper(getKey(), other.getKey()) && UtilObject.equalsHelper(getValue(), other.getValue()); + } + + public int hashCode() { + return UtilObject.doHashCode(getKey()) ^ UtilObject.doHashCode(getValue()); + } +} Added: ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapEntrySet.java URL: http://svn.apache.org/viewvc/ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapEntrySet.java?rev=885275&view=auto ============================================================================== --- ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapEntrySet.java (added) +++ ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapEntrySet.java Sun Nov 29 21:26:37 2009 @@ -0,0 +1,48 @@ +/******************************************************************************* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + *******************************************************************************/ +package org.ofbiz.base.util.collections; + +import java.util.Map; +import java.util.Set; + +public abstract class GenericMapEntrySet<K, V, M extends GenericMap<K, V>> extends GenericMapSet<K, V, M, Map.Entry<K, V>> { + public GenericMapEntrySet(M source) { + super(source); + } + + public boolean contains(Object item) { + if (item == null) return false; + if (!(item instanceof Map.Entry)) return false; + Map.Entry other = (Map.Entry) item; + return contains(other.getKey(), other.getValue()); + } + + protected abstract boolean contains(Object key, Object value); + + public boolean remove(Object item) { + if (item == null) return false; + if (!(item instanceof Map.Entry)) return false; + Map.Entry other = (Map.Entry) item; + Object key = other.getKey(); + if (!source.containsKey(key)) return false; + source.remove(key); + return true; + } +} + Added: ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapKeySet.java URL: http://svn.apache.org/viewvc/ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapKeySet.java?rev=885275&view=auto ============================================================================== --- ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapKeySet.java (added) +++ ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapKeySet.java Sun Nov 29 21:26:37 2009 @@ -0,0 +1,33 @@ +/******************************************************************************* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + *******************************************************************************/ +package org.ofbiz.base.util.collections; + +import java.util.Map; +import java.util.Set; + +public abstract class GenericMapKeySet<K, V, M extends Map<K, V>> extends GenericMapSet<K, V, M, K> { + public GenericMapKeySet(M source) { + super(source); + } + + public boolean remove(Object item) { + return source.remove(item) != null; + } +} + Added: ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapSet.java URL: http://svn.apache.org/viewvc/ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapSet.java?rev=885275&view=auto ============================================================================== --- ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapSet.java (added) +++ ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapSet.java Sun Nov 29 21:26:37 2009 @@ -0,0 +1,48 @@ +/******************************************************************************* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + *******************************************************************************/ +package org.ofbiz.base.util.collections; + +import java.util.Map; +import java.util.Set; + +public abstract class GenericMapSet<K, V, M extends Map<K, V>, I> extends GenericMapCollection<K, V, M, I> implements Set<I> { + public GenericMapSet(M source) { + super(source); + } + + public final boolean equals(Object o) { + if (!(o instanceof Set)) return false; + Set other = (Set) o; + if (source.size() != other.size()) return false; + for (I item: this) { + if (!other.contains(item)) return false; + } + return true; + } + + public final int hashCode() { + int h = 0; + for (I item: this) { + if (item == null) continue; + h += item.hashCode(); + } + return h; + } +} + Added: ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapValues.java URL: http://svn.apache.org/viewvc/ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapValues.java?rev=885275&view=auto ============================================================================== --- ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapValues.java (added) +++ ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/GenericMapValues.java Sun Nov 29 21:26:37 2009 @@ -0,0 +1,77 @@ +/******************************************************************************* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + *******************************************************************************/ +package org.ofbiz.base.util.collections; + +import java.util.Collection; +import java.util.Iterator; +import java.util.List; +import java.util.Map; +import java.util.Set; + +import org.ofbiz.base.util.UtilObject; + +public abstract class GenericMapValues<K, V, M extends Map<K, V>> extends GenericMapCollection<K, V, M, V> { + public GenericMapValues(M source) { + super(source); + } + + public boolean contains(Object item) { + Iterator<V> it = iterator(false); + while (it.hasNext()) { + if (UtilObject.equalsHelper(item, it.next())) return true; + } + return false; + } + + public boolean equals(Object o) { + if (!(o instanceof Collection)) return false; + if (o instanceof List || o instanceof Set) return false; + Collection other = (Collection) o; + if (source.size() != other.size()) return false; + Iterator<V> it = iterator(false); + while (it.hasNext()) { + V item = it.next(); + if (!other.contains(item)) return false; + } + return true; + } + + public int hashCode() { + int h = 0; + Iterator<V> it = iterator(false); + while (it.hasNext()) { + V item = it.next(); + if (item == null) continue; + h += item.hashCode(); + } + return h; + } + + public boolean remove(Object item) { + Iterator<V> it = iterator(false); + while (it.hasNext()) { + if (UtilObject.equalsHelper(item, it.next())) { + it.remove(); + return true; + } + } + return false; + } +} + Added: ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/IteratorWrapper.java URL: http://svn.apache.org/viewvc/ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/IteratorWrapper.java?rev=885275&view=auto ============================================================================== --- ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/IteratorWrapper.java (added) +++ ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/IteratorWrapper.java Sun Nov 29 21:26:37 2009 @@ -0,0 +1,62 @@ +/******************************************************************************* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + *******************************************************************************/ +package org.ofbiz.base.util.collections; + +import java.util.Iterator; +import java.util.NoSuchElementException; + +public abstract class IteratorWrapper<DEST, SRC> implements Iterator<DEST> { + private final Iterator<? extends SRC> it; + private DEST lastDest; + private SRC lastSrc; + + protected IteratorWrapper(Iterator<? extends SRC> it) { + this.it = it; + } + + public boolean hasNext() { + return it.hasNext(); + } + + public DEST next() { + try { + lastSrc = it.next(); + return lastDest = convert(lastSrc); + } catch (NoSuchElementException e) { + lastDest = null; + lastSrc = null; + throw e; + } + } + + public void remove() { + if (lastSrc != null) { + it.remove(); + noteRemoval(lastDest, lastSrc); + lastDest = null; + lastSrc = null; + } else { + throw new IllegalStateException(); + } + } + + protected abstract void noteRemoval(DEST dest, SRC src); + protected abstract DEST convert(SRC src); +} + Added: ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/ReadOnlyMapEntry.java URL: http://svn.apache.org/viewvc/ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/ReadOnlyMapEntry.java?rev=885275&view=auto ============================================================================== --- ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/ReadOnlyMapEntry.java (added) +++ ofbiz/trunk/framework/base/src/org/ofbiz/base/util/collections/ReadOnlyMapEntry.java Sun Nov 29 21:26:37 2009 @@ -0,0 +1,59 @@ +/******************************************************************************* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + *******************************************************************************/ +package org.ofbiz.base.util.collections; + +import java.util.Map; + +import org.ofbiz.base.util.UtilObject; + +/** this class can go away when ofbiz switches to java 1.6, replaced by + * AbstractMap.SimpleImmutableEntry + */ +public class ReadOnlyMapEntry<K, V> implements Map.Entry<K, V> { + protected final K key; + protected final V value; + + public ReadOnlyMapEntry(K key, V value) { + this.key = key; + this.value = value; + } + + public K getKey() { + return key; + } + + public V getValue() { + return value; + } + + public V setValue(V value) { + throw new UnsupportedOperationException(); + } + + public boolean equals(Object o) { + if (!(o instanceof Map.Entry)) return false; + if (this == o) return true; + Map.Entry other = (Map.Entry) o; + return UtilObject.equalsHelper(getKey(), other.getKey()) && UtilObject.equalsHelper(getValue(), other.getValue()); + } + + public int hashCode() { + return UtilObject.doHashCode(getKey()) ^ UtilObject.doHashCode(getValue()); + } +} |
| Free forum by Nabble | Edit this page |
