Multimap für .NET? ($Edit)



  • Hallo miteinander,

    Gibt es für .NET eine Klasse, welche eine Art Multimap, wie sie es aus C++ kennt, implementiert? Konkret möchte ich gerne zufälligen Nummern keinen, einen oder mehrere Datensätze zuordnen. Hat jemand eine generische Lösung, oder muss ich Dictionary<int, List<bla>> benutzen?

    FG.





  • Inwiefern hilft mir das? Die Keys müssen ja wieder unique sein?

    $Edit: Ich hätte wohl eher sagen sollen "Multimap" 💡



  • Habe eine Lösung gefunden, die für meine Zwecke ausreichen sollte: http://www.dotnetperls.com/multimap



  • Eventuell solltest du den Typen des Keys ebenfalls generisch machen. - Auch wenn du derzeit nur Integer brauchst, bietet sich das aus meiner Sicht an.

    Ich könnte mir das angepasst in etwa wie Folgt (ungetestet) vorstellen:

    public class MultiMap<TKey, TValue>
    {
        #region Fields
    
        private Dictionary<TKey, List<TValue>> _innerDictionary = new Dictionary<TKey, List<TValue>>();
    
        #endregion
    
        #region Properties
    
        /// <summary>
        /// gets the collection for the given key
        /// </summary>
        /// <param name="key">the key</param>
        /// <returns>the collection</returns>
        public List<TValue> this[TKey key]
        {
            get
            {
                List<TValue> values = new List<TValue>();
                if (!this._innerDictionary.TryGetValue(key, out values))
                {
                    this._innerDictionary.Add(key, values);
                }
                return values;
            }
            set
            {
                if (this._innerDictionary.ContainsKey(key))
                    this._innerDictionary[key] = value;
                else
                    this._innerDictionary.Add(key, value);                
            }
        }
    
        /// <summary>
        /// gets an item from an mapping at a given index
        /// </summary>
        /// <param name="key">the key</param>
        /// <param name="index">the index</param>
        /// <returns>the value</returns>
        public TValue this[TKey key, int index]
        {
            get
            {
                TValue item = default(TValue);
                if (index > 0 && index < this[key].Count)
                    item = this[key][index];
                return item;
            }
        }
    
        /// <summary>
        /// gets the collection of keys
        /// </summary>
        public IEnumerable<TKey> Keys
        {
            get
            {
                return this._innerDictionary.Keys;
            }
        }
    
        #endregion
    
        #region Methods
    
        /// <summary>
        /// Method to add a mapping
        /// </summary>
        /// <param name="key">the key</param>
        /// <param name="values">the values</param>
        public void Add(TKey key, List<TValue> values)
        {
            this[key] = values;
        }
    
        /// <summary>
        /// Method to add an item to a mapping
        /// </summary>
        /// <param name="key">the key</param>
        /// <param name="item">the item</param>
        public void AddItem(TKey key, TValue item)
        {
            this[key].Add(item);
        }
    
        /// <summary>
        /// Method to remove a mapping
        /// </summary>
        /// <param name="key">the key</param>
        /// <returns>true if the mapping successfully removed</returns>
        public bool Remove(TKey key)
        {
            return this._innerDictionary.Remove(key);
        }
    
        /// <summary>
        /// Method to remove an item from an mapping
        /// </summary>
        /// <param name="key">the key</param>
        /// <param name="value">the value</param>
        /// <returns>true if the item removed successfull</returns>
        public bool RemoveItem(TKey key, TValue value)
        {
            return this[key].Remove(value);
        }
    
        /// <summary>
        /// Method to check if the map contains a given key
        /// </summary>
        /// <param name="key">the key</param>
        /// <returns>true if the map contains the key</returns>
        public bool ContainsKey(TKey key)
        {
            return this._innerDictionary.ContainsKey(key);
        }
    
        #endregion
    }
    


  • Super vielen lieben Dank. Das ist noch ein Service hier! 👍



  • /rant/ schrieb:

    public class MultiMap<TKey, TValue>
    {
    
        /// <summary>
        /// gets the collection for the given key
        /// </summary>
        /// <param name="key">the key</param>
        /// <returns>the collection</returns>
        public List<TValue> this[TKey key]
        {
            get
            {
                List<TValue> values = new List<TValue>();
                if (!this._innerDictionary.TryGetValue(key, out values))
                {
                    this._innerDictionary.Add(key, values);
                }
                return values;
            }
            set
            {
     ...        
            }
        }
    }
    

    Das ist hoffentlich nicht dein Ernst...

    Abgesehen davon dass das verschwänderisch ist, ist es sogar falsch. Das fügt dir null ein wenn auf einen nicht existierenden Key zugegeiffen wird. Wobei man um das zu sehen nichtmal wissen muss was TryGetValue genau tut. TryGetValue MUSS den out Parameter überschreiben, das ist nunmal die Regel bei out Parametern.

    public class MultiMap<TKey, TValue>
    {
    
        /// <summary>
        /// gets the collection for the given key
        /// </summary>
        /// <param name="key">the key</param>
        /// <returns>the collection</returns>
        public List<TValue> this[TKey key]
        {
            get
            {
                List<TValue> values;
                if (!this._innerDictionary.TryGetValue(key, out values))
                {
                    values = new List<TValue>();
                    this._innerDictionary.Add(key, values);
                }
                return values;
            }
            set
            {
     ...        
            }
        }
    }
    

Anmelden zum Antworten