Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- using System;
- using System.Collections;
- using System.Collections.Generic;
- using System.Runtime.InteropServices;
- public class EnumKeyDictionary<TKey, TValue> : IDictionary<TKey, TValue>
- {
- private Dictionary<int, TValue> data;
- private KeyCollection keys;
- public TValue this[TKey key] { get { return data[ToIntKey(key)]; } set { data[ToIntKey(key)] = value; } }
- public KeyCollection Keys
- {
- get
- {
- if (keys == null)
- {
- keys = new KeyCollection(this);
- }
- return keys;
- }
- }
- ICollection<TKey> IDictionary<TKey, TValue>.Keys
- {
- get
- {
- if (keys == null)
- {
- keys = new KeyCollection(this);
- }
- return keys;
- }
- }
- public Dictionary<int, TValue>.ValueCollection Values => data.Values;
- ICollection<TValue> IDictionary<TKey, TValue>.Values => data.Values;
- public int Count => data.Count;
- public bool IsReadOnly => false;
- public EnumKeyDictionary()
- {
- data = new Dictionary<int, TValue>();
- }
- public EnumKeyDictionary(int capacity)
- {
- data = new Dictionary<int, TValue>(capacity);
- }
- public EnumKeyDictionary(IDictionary<TKey, TValue> dictionary)
- {
- var capacity = dictionary != null ? dictionary.Count : 0;
- data = new Dictionary<int, TValue>(capacity);
- foreach (var pair in dictionary)
- {
- Add(pair.Key, pair.Value);
- }
- }
- private static int ToIntKey(TKey key)
- {
- return EnumSupport.ToInt<TKey>(key);
- }
- private static TKey ToEnumKey(int key)
- {
- return EnumSupport.ToEnum32<TKey>(key);
- }
- private static KeyValuePair<TKey, TValue> GetKeyValuePair(int key, TValue value)
- {
- return new KeyValuePair<TKey, TValue>(ToEnumKey(key), value);
- }
- private static KeyValuePair<TKey, TValue> GetKeyValuePair(KeyValuePair<int, TValue> pair)
- {
- return GetKeyValuePair(pair.Key, pair.Value);
- }
- public void Add(TKey key, TValue value)
- {
- data.Add(ToIntKey(key), value);
- }
- public void Clear()
- {
- data.Clear();
- }
- public bool ContainsKey(TKey key)
- {
- return data.ContainsKey(ToIntKey(key));
- }
- public bool Remove(TKey key)
- {
- return data.Remove(ToIntKey(key));
- }
- public bool TryGetValue(TKey key, out TValue value)
- {
- return data.TryGetValue(ToIntKey(key), out value);
- }
- public void CopyTo(KeyValuePair<TKey, TValue>[] array, int arrayIndex)
- {
- if (array == null)
- {
- throw new ArgumentNullException("array is null");
- }
- foreach (var pair in data)
- {
- array[arrayIndex++] = GetKeyValuePair(pair);
- }
- }
- public TValue GetOrDefault(TKey key)
- {
- var value = default(TValue);
- if (TryGetValue(key, out value))
- {
- return value;
- }
- return default(TValue);
- }
- public Enumerator GetEnumerator()
- {
- return new Enumerator(this);
- }
- void ICollection<KeyValuePair<TKey, TValue>>.Add(KeyValuePair<TKey, TValue> item)
- {
- Add(item.Key, item.Value);
- }
- bool ICollection<KeyValuePair<TKey, TValue>>.Contains(KeyValuePair<TKey, TValue> item)
- {
- var key = ToIntKey(item.Key);
- if (data.ContainsKey(key))
- {
- return EqualityComparer<TValue>.Default.Equals(data[key], item.Value);
- }
- return false;
- }
- bool ICollection<KeyValuePair<TKey, TValue>>.Remove(KeyValuePair<TKey, TValue> item)
- {
- var key = ToIntKey(item.Key);
- if (data.ContainsKey(key) && EqualityComparer<TValue>.Default.Equals(data[key], item.Value))
- {
- Remove(item.Key);
- return true;
- }
- return false;
- }
- IEnumerator<KeyValuePair<TKey, TValue>> IEnumerable<KeyValuePair<TKey, TValue>>.GetEnumerator()
- {
- return new Enumerator(this);
- }
- IEnumerator IEnumerable.GetEnumerator()
- {
- return new Enumerator(this);
- }
- public struct Enumerator : IEnumerator<KeyValuePair<TKey, TValue>>
- {
- private EnumKeyDictionary<TKey, TValue> dictionary;
- private Dictionary<int, TValue>.Enumerator enumerator;
- public KeyValuePair<TKey, TValue> Current
- {
- get
- {
- return GetKeyValuePair(enumerator.Current);
- }
- }
- object IEnumerator.Current
- {
- get
- {
- return GetKeyValuePair(enumerator.Current);
- }
- }
- public Enumerator(EnumKeyDictionary<TKey, TValue> dictionary)
- {
- this.dictionary = dictionary;
- enumerator = dictionary.data.GetEnumerator();
- }
- public void Dispose()
- {
- }
- public bool MoveNext()
- {
- return enumerator.MoveNext();
- }
- void IEnumerator.Reset()
- {
- enumerator = dictionary.data.GetEnumerator();
- }
- }
- public sealed class KeyCollection : ICollection<TKey>
- {
- private EnumKeyDictionary<TKey, TValue> dictionary;
- public int Count => dictionary.Count;
- public bool IsReadOnly => true;
- public KeyCollection(EnumKeyDictionary<TKey, TValue> dictionary)
- {
- this.dictionary = dictionary;
- }
- public void CopyTo(TKey[] array, int arrayIndex)
- {
- if (array == null)
- {
- throw new ArgumentNullException("array is null");
- }
- foreach (var pair in dictionary)
- {
- array[arrayIndex++] = pair.Key;
- }
- }
- bool ICollection<TKey>.Contains(TKey item)
- {
- return dictionary.ContainsKey(item);
- }
- void ICollection<TKey>.Add(TKey item)
- {
- throw new NotSupportedException("Not Supprot KeyCollection Set");
- }
- void ICollection<TKey>.Clear()
- {
- throw new NotSupportedException("Not Supprot KeyCollection Set");
- }
- bool ICollection<TKey>.Remove(TKey item)
- {
- throw new NotSupportedException("Not Supprot KeyCollection Set");
- }
- public Enumerator GetEnumerator()
- {
- return new Enumerator(dictionary);
- }
- IEnumerator<TKey> IEnumerable<TKey>.GetEnumerator()
- {
- return new Enumerator(dictionary);
- }
- IEnumerator IEnumerable.GetEnumerator()
- {
- return new Enumerator(dictionary);
- }
- public struct Enumerator : IEnumerator<TKey>
- {
- private EnumKeyDictionary<TKey, TValue> dictionary;
- private Dictionary<int, TValue>.Enumerator enumerator;
- public TKey Current
- {
- get
- {
- return ToEnumKey(enumerator.Current.Key);
- }
- }
- object IEnumerator.Current
- {
- get
- {
- return ToEnumKey(enumerator.Current.Key);
- }
- }
- public Enumerator(EnumKeyDictionary<TKey, TValue> dictionary)
- {
- this.dictionary = dictionary;
- enumerator = dictionary.data.GetEnumerator();
- }
- public void Dispose()
- {
- }
- public bool MoveNext()
- {
- return enumerator.MoveNext();
- }
- void IEnumerator.Reset()
- {
- enumerator = dictionary.data.GetEnumerator();
- }
- }
- }
- public class EnumSupport
- {
- #if PLATFORM_SUPPORTS_MONO
- class ValueCastTo<TTo>
- {
- [StructLayout(LayoutKind.Explicit)]
- struct Reinterpret<TFrom>
- {
- [FieldOffset(0)] public TFrom From;
- [FieldOffset(0)] public TTo To;
- }
- public static TTo From<TFrom>(TFrom from)
- {
- var r = default(Reinterpret<TFrom>);
- r.From = from;
- return r.To;
- }
- }
- #elif false
- // C# 7.3 ~
- class EnumCaster<TEnum> where TEnum : unmanaged, Enum
- {
- public static TResult To<TResult>(TEnum value) where TResult : unmanaged
- {
- unsafe
- {
- TResult outVal = default;
- Buffer.MemoryCopy(&value, &outVal, sizeof(TResult), sizeof(TEnum));
- return outVal;
- }
- }
- public static TEnum From<TSource>(TSource value) where TSource : unmanaged
- {
- unsafe
- {
- TEnum outVal = default;
- long size = sizeof(TEnum) < sizeof(TSource) ? sizeof(TEnum) : sizeof(TSource);
- Buffer.MemoryCopy(&value, &outVal, sizeof(TEnum), size);
- return outVal;
- }
- }
- }
- class ValueCastTo<TTo>
- {
- static bool isEnum = typeof(TTo).IsEnum;
- public static TTo From<TFrom>(TFrom from)
- {
- if (isEnum)
- {
- return EnumCaster<TTo>.From(from);
- }
- else
- {
- return EnumCaster<TFrom>.To(from);
- }
- }
- }
- #else
- // others (without AOT)
- class ValueCastTo<TTo>
- {
- class Cache<TFrom>
- {
- public static readonly Func<TFrom, TTo> Caster = Get();
- static Func<TFrom, TTo> Get()
- {
- var p = Expression.Parameter(typeof(TFrom), "from");
- var c = Expression.ConvertChecked(p, typeof(TTo));
- return Expression.Lambda<Func<TFrom, TTo>>(c, p).Compile();
- }
- }
- public static TTo From<TFrom>(TFrom from) where TFrom : struct
- {
- return Cache<TFrom>.Caster(from);
- }
- }
- #endif
- public static int ToInt<T>(T e)
- {
- return ValueCastTo<int>.From(e);
- }
- public static T ToEnum32<T>(int value)
- {
- return ValueCastTo<T>.From(value);
- }
- }
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement