Microbubu的迷你实验室

C#中的IEnumerator接口和IEumerable接口

字数统计: 672阅读时长: 3 min
2018/11/08 Share

目标

  1. 自己实现一个简易的Dictionary字典.
  2. 实现泛型IEnumerator和IEnumerable接口.

简易Dictionary

KeyValuePair数据结构定义

1
2
3
4
5
public class MyKeyValuePair<TKey, TValue>
{
public TKey Key { get; set; }
public TValue Value { get; set; }
}

简易Dictionary实现

不考虑线程安全问题,实现最基本的字典的功能。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
public class MyDictionary<TKey, TValue>
{
private List<MyKeyValuePair<TKey, TValue>> pairs;

public MyDictionary()
{
pairs = new List<MyKeyValuePair<TKey, TValue>>();
}

//索引器
public TValue this[TKey key]
{
get
{
foreach (var v in pairs)
{
if (v.Key.Equals(key))
return v.Value;
}
throw new KeyNotFoundException();
}
set
{
foreach (var v in pairs)
{
if (v.Key.Equals(key))
v.Value = value;
}
}
}

public bool ContainsKey(TKey key)
{
foreach (var item in pairs)
{
if (item.Key.Equals(key))
return true;
}
return false;
}

public void Add(TKey key, TValue value)
{
if (ContainsKey(key))
this[key] = value;
else
pairs.Add(new MyKeyValuePair<TKey, TValue>() { Key = key, Value = value });
}
}

泛型IEnumerator接口

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
class MyDictionaryEnumerator<TKey,TValue> : IEnumerator<MyKeyValuePair<TKey, TValue>>
{
private List<MyKeyValuePair<TKey, TValue>> pairs;
private int index = -1;
private MyKeyValuePair<TKey, TValue> current;

public MyDictionaryEnumerator(List<MyKeyValuePair<TKey,TValue>> p)
{
pairs = p;
}

MyKeyValuePair<TKey, TValue> IEnumerator<MyKeyValuePair<TKey, TValue>>.Current => current;

object IEnumerator.Current => current;

void IDisposable.Dispose()
{
pairs.Clear();
}

bool IEnumerator.MoveNext()
{
index++;
if (index >= pairs.Count)
return false;

current = pairs[index];
return true;
}

void IEnumerator.Reset()
{
index = 0;
}
}

实现泛型IEnumerable接口的Dictionary

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
public class MyDictionary<TKey, TValue> : IEnumerable<MyKeyValuePair<TKey,TValue>>
{
private List<MyKeyValuePair<TKey, TValue>> pairs;

public MyDictionary()
{
pairs = new List<MyKeyValuePair<TKey, TValue>>();
}

public TValue this[TKey key]
{
get
{
foreach (var v in pairs)
{
if (v.Key.Equals(key))
return v.Value;
}
throw new KeyNotFoundException();
}
set
{
foreach (var v in pairs)
{
if (v.Key.Equals(key))
v.Value = value;
}
}
}

public bool ContainsKey(TKey key)
{
foreach (var item in pairs)
{
if (item.Key.Equals(key))
return true;
}
return false;
}

public void Add(TKey key, TValue value)
{
if (ContainsKey(key))
this[key] = value;
else
pairs.Add(new MyKeyValuePair<TKey, TValue>() { Key = key, Value = value });
}

IEnumerator IEnumerable.GetEnumerator()
{
return new MyDictionaryEnumerator<TKey, TValue>(pairs);
}

IEnumerator<MyKeyValuePair<TKey, TValue>> IEnumerable<MyKeyValuePair<TKey, TValue>>.GetEnumerator()
{
return new MyDictionaryEnumerator<TKey, TValue>(pairs);
}
}

测试

问题描述:查找出一串字符中第一个重复出现的字符,要求不能使用系统中已经存在的数据结构。这是之前去面试华为的时候面试官现场给出的题,既然不能使用系统中已有的字典,那么可以自己定义一个字典类型,将要使用的方法封装进去即可。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
char GetFirstRepeatCharacter(string str)
{
var dictionary = new MyDictionary<char, int>();

foreach (var v in str)
{
if (dictionary.ContainsKey(v))
{
dictionary[v]++;
continue;
}
dictionary.Add(v, 1);
}

foreach (var v in dictionary)
{
if (v.Value > 1) return v.Key;
}

return '\0'; //没有不重复的字符
}
CATALOG
  1. 1. 目标
  2. 2. 简易Dictionary
    1. 2.1. KeyValuePair数据结构定义
    2. 2.2. 简易Dictionary实现
  3. 3. 泛型IEnumerator接口
  4. 4. 实现泛型IEnumerable接口的Dictionary
  5. 5. 测试