Пример #1
0
        protected virtual void Rehash(int newCapacity, OpenHashMapBase <K, V> source)
        {
            var fillFactor = FillFactorForSize(m_size);

            m_threshold = (int)(newCapacity * fillFactor);
            m_mask      = newCapacity - 1;
            m_mask2     = newCapacity * 2 - 1;

            object[] sourceData = source.m_data;

            m_data = new object[newCapacity * 2];
            m_size = m_hasNull ? 1 : 0;
            //Arrays.Fill(m_data, FreeKey); // not needed any more, since FreeKey is null

            int oldLength = sourceData.Length;

            for (int i = 0; i < oldLength; i += 2)
            {
                object oldKey = sourceData[i];
                if (oldKey != FreeKey && oldKey != RemovedKey)
                {
                    Put((K)oldKey, (V)sourceData[i + 1], false);
                }
            }
        }
Пример #2
0
        public bool Remove(TKey key)
        {
            lock (_sync)
            {
                var map = _writeMap;

                if (map != null)
                {
                    if (!_writeMap.Remove(key))
                    {
                        return(false);
                    }
                    _readMap  = _writeMap;
                    _writeMap = null;
                    _writeMapAccessCounter = 0;
                    return(true);
                }

                map = _readMap;
                if (!_readMap.Contains(key))
                {
                    return(false);
                }
                map = CloneMap(map, map.Size - 1);
                map.Remove(key);
                _readMap = map;
                return(true);
            }
        }
Пример #3
0
        protected override void Rehash(int newCapacity, OpenHashMapBase <K, V> source)
        {
            var other = source as OpenEqualityComparerHashMap <K, V>;

            if (_comparer == null && other != null)
            {
                _comparer = other._comparer;
            }
            base.Rehash(newCapacity, source);
        }
Пример #4
0
 internal FastConcurrentHashMap(bool useIdentityComparison)
 {
     if (useIdentityComparison)
     {
         _readMap = new OpenIdentityHashMap <TKey, TVal>(DefaultSize, DefaultFillFactor, DefaultFillFactor2Threshold, DefaultFillFactor2);
     }
     else
     {
         _readMap = new OpenHashMap <TKey, TVal>(DefaultSize, DefaultFillFactor, DefaultFillFactor2Threshold, DefaultFillFactor2);
     }
 }
Пример #5
0
        public void Clear()
        {
            var empty = CloneMap(_readMap, -1);

            lock (_sync)
            {
                _readMap  = empty;
                _writeMap = null;
                _writeMapAccessCounter = 0;
            }
        }
Пример #6
0
        /// <summary>
        /// Clones the hash map.
        /// </summary>
        protected OpenHashMapBase(OpenHashMapBase <K, V> other, int newSize)
        {
            m_fillFactor           = other.m_fillFactor;
            m_fillFactor2          = other.m_fillFactor2;
            m_fillFactor2Threshold = other.m_fillFactor2Threshold;

#if HASH_MAP_PERFORMANCE
            m_totalAccesses = other.m_totalAccesses;
            m_totalGets     = other.m_totalGets;
#endif

            if (newSize < 0)
            {
                InitializeEmpty(DefaultSize);
                return;
            }

            if (newSize < other.m_size)
            {
                newSize = other.m_size;
            }

            if (newSize < DefaultSize)
            {
                newSize = DefaultSize;
            }

            m_mask      = other.m_mask;
            m_mask2     = other.m_mask2;
            m_threshold = other.m_threshold;

            m_hasNull   = other.m_hasNull;
            m_nullValue = other.m_nullValue;

            int newCapacity = Tools.ArraySize(newSize, FillFactorForSize(newSize));

            if (2 * newCapacity == other.m_data.Length)
            {
                m_data = Arrays.CopyOf(other.m_data, other.m_data.Length);
                m_size = other.m_size;
            }
            else
            {
                Rehash(newCapacity, other);
            }
        }
Пример #7
0
        public TVal PutIfAbsent(TKey key, TVal value)
        {
            if (value == null)
            {
                throw new ArgumentNullException();
            }

            lock (_sync)
            {
                _writeMapAccessCounter = Math.Max(_writeMapAccessCounter - 1, 0);

                var map = _writeMap;
                if (map == null)
                {
                    var baseMap = _readMap;
                    map       = CloneMap(baseMap, baseMap.Size + 1);
                    _writeMap = map;
                }

                return(map.PutIfAbsent(key, value));
            }
        }
Пример #8
0
        public TVal Get(TKey key)
        {
            // Try the fast path.
            var ret = _readMap.Get(key);

            if (ret != null)
            {
                return(ret);
            }

            // This second volatile field access is not strictly required for a caching map,
            // that will 'PutIfAbsent' or 'Put' if we return null anyway. For those types it
            // would suffice if we always return null, or make the write map non-volatile.
            // As a caching map will on the other hand hopefully most of the time have
            // cache-hits, this volatile access should not hurt too much.
            if (_writeMap == null)
            {
                return(default(TVal));
            }

            // walk the slow path.
            lock (_sync)
            {
                ++_writeMapAccessCounter;

                var map = _writeMap;

                if (++_writeMapAccessCounter > CopyWriteMapAfterThreshold)
                {
                    // Set the read map after a number of servings from the write map.
                    _readMap  = map;
                    _writeMap = null;
                    _writeMapAccessCounter = 0;
                }

                return(map.Get(key));
            }
        }
Пример #9
0
 public FastConcurrentHashMap(IEqualityComparer <TKey> comparer)
 {
     _readMap = new OpenEqualityComparerHashMap <TKey, TVal>(comparer, DefaultSize, DefaultFillFactor, DefaultFillFactor2Threshold, DefaultFillFactor2);
 }
Пример #10
0
 internal FastConcurrentHashMap(OpenHashMapBase <TKey, TVal> readMap)
 {
     _readMap = readMap;
 }
Пример #11
0
 private static OpenHashMapBase <TKey, TVal> CloneMap(OpenHashMapBase <TKey, TVal> map, int newSize)
 {
     return((OpenHashMapBase <TKey, TVal>)map.Clone(newSize));
 }
Пример #12
0
 public Enumerator(OpenHashMapBase <K, V> map)
     : base(map)
 {
 }
Пример #13
0
 public ValueCollection(OpenHashMapBase <K, V> map)
 {
     m_map = map;
 }
Пример #14
0
 public KeyCollection(OpenHashMapBase <K, V> map)
 {
     m_map = map;
 }
Пример #15
0
 protected EnumeratorBase(OpenHashMapBase <K, V> map)
 {
     m_map      = map;
     m_position = InitialPosition;
 }