4.本例中,字典集合裡的一個元素是由鍵和值組成的,這一個元素使用了FCL中現成的DictionaryEntry來實現,它定義了可設置或檢索的字典鍵/值對。
下面列出了代碼,請大家參照注釋進行理解。
IDictionary接口的實現(以下代碼可直接拷貝並運行)
using System;
using System.Collections;
public class SimpleDictionary : IDictionary
{
private DictionaryEntry[] items; //用數組存放元素
private Int32 ItemsInUse = 0; //元素個數
//指定存儲空間的構造方法
public SimpleDictionary(Int32 numItems)
{
items = new DictionaryEntry[numItems];
}
#region IDictionary 成員
public bool IsReadOnly { get { return false; } }
public bool Contains(object key)
{ //檢測是否包含指定的key鍵
Int32 index;
return TryGetIndexOfKey(key, out index);
}
public bool IsFixedSize { get { return false; } }
public void Remove(object key)
{ //移除指定鍵的元素
Int32 index;
if (TryGetIndexOfKey(key, out index))
{ //把移除元素後面的所有元素向前移動一個位置
Array.Copy(items, index + 1, items, index, ItemsInUse - index - 1);
ItemsInUse--;
}
}
public void Clear() { ItemsInUse = 0; } //清除所有元素
public void Add(object key, object value)
{ //添加一個元素
items[ItemsInUse++] = new DictionaryEntry(key, value);
}
public ICollection Keys
{ //返回所有鍵的集合
get
{ //把所有鍵的集合拷貝到新數組中並返回
Object[] keys = new Object[ItemsInUse];
for (Int32 n = 0; n < ItemsInUse; n++)
keys[n] = items[n].Key;
return keys;
}
}
public ICollection Values
{ //返回所有值的集合
get
{ //把所有值的集合拷貝到新數組中並返回
Object[] values = new Object[ItemsInUse];
for (Int32 n = 0; n < ItemsInUse; n++)
values[n] = items[n].Value;
return values;
}
}
public object this[object key]
{ //item屬性的實現,也就是索引器
get
{
Int32 index;
if (TryGetIndexOfKey(key, out index))
{
return items[index].Value;
}
return null;
}
set
{
Int32 index;
if (TryGetIndexOfKey(key, out index))
{
items[index].Value = value;
}
else
{
Add(key, value);
}
}
}
//這個方法有兩個作用,第一是查找指定鍵是否存在
//第二是返回指定鍵的索引
private Boolean TryGetIndexOfKey(Object key, out Int32 index)
{
for (index = 0; index < ItemsInUse; index++)
{
if (items[index].Key.Equals(key)) return true;
}
return false;
}
//用於迭代的嵌套類,它同時實現了IEnumerator和IDictionaryEnumerator
private class SimpleDictionaryEnumerator : IDictionaryEnumerator
{
DictionaryEntry[] items;
Int32 index = -1;
//構造方法,用於獲得SimpleDictionary類的所有元素
public SimpleDictionaryEnumerator(SimpleDictionary sd)
{
items = new DictionaryEntry[sd.Count];
Array.Copy(sd.items, 0, items, 0, sd.Count);
}
public Object Current
{
get { return items[index]; }
}
public DictionaryEntry Entry
{
get { return (DictionaryEntry) Current; }
}
public Object Key { get { return items[index].Key; } }
public Object Value { get { return items[index].Value; } }
public Boolean MoveNext()
{
if (index < items.Length - 1) { index++; return true; }
return false;
}
public void Reset()
{
index = -1;
}
}
//實現IDictionary接口中的GetEnumerator方法
public IDictionaryEnumerator GetEnumerator()
{
return new SimpleDictionaryEnumerator(this);
}
#endregion
#region ICollection 成員
public bool IsSynchronized { get { return false; } }
//這句夠簡化,直接彈出異常不給使用
public object SyncRoot { get { throw new NotImplementedException(); } }
public int Count { get { return ItemsInUse; } }
public void CopyTo(Array array, int index) { throw new NotImplementedException(); }
#endregion
#region IEnumerable 成員
//實現IEnumerable接口的GetEnumerator方法
IEnumerator IEnumerable.GetEnumerator()
{
// 這裡使用了強制類型轉換.
return ((IDictionary)this).GetEnumerator();
}
#endregion
}
public sealed class App
{
static void Main()
{
// 創建一個只能包含三個元素的字典類
IDictionary d = new SimpleDictionary(3);
// 添加三個人名和它們的年齡到字典內
d.Add("Jeff", 40);
d.Add("Kristin", 34);
d.Add("Aidan", 1);
Console.WriteLine("字典元素個數= {0}", d.Count);
Console.WriteLine("字典中是否包含'Jeff'? {0}", d.Contains("Jeff"));
Console.WriteLine("Jeff的年齡是:{0}", d["Jeff"]);
// 顯示字典中的所有鍵和值,由於實現了IDictionaryEnumerator接口
//所以可以使用foreach進行調用
foreach (DictionaryEntry de in d)
{
Console.WriteLine("{0} is {1} years old.", de.Key, de.Value);
}
// 移除“Jeff”
d.Remove("Jeff");
// 移除不存在的元素不會引發異常
d.Remove("Max");
// 顯示字典中的所有人名(key)
foreach (String s in d.Keys)
Console.WriteLine(s);
// 顯示字典中的所有年齡(value)
foreach (Int32 age in d.Values)
Console.WriteLine(age);
}
}