我试图理解编写实现泛型的现有代码片段,因此它设置了一个通用字典,然后将项目添加到字典中,其中键是类型,值是委托
private readonly Dictionary<Type, Func<actionType, Task>> requestedActions;
private void AddAction<T>(Func<T, Task> action) where T : actionType
{
this.requestedActions[typeof(T)] = (request) => action((T)request);
}
this.AddAction<AddItem>(this.HandleAdd);
this.AddAction<UpdateItem>(this.HandleUpdate);
this.AddAction<DeleteItem>(this.HandleDelete);
private Task HandleAdd(AddItem message)
{
.....
}
然后当收到某个动作时,它会执行相关的委托
public bool ProcessData(ItemMessage request)
{
Func<ItemMessage, Task> requestAction;
if (this.requestedActions.TryGetValue(requestType, out requestAction))
{
requestAction(request).Await();
}
}
为什么这种方法会优先于/类似于actionType上的switch语句,就好像添加了新类型一样,你仍然需要将新类型添加到字典中并实现新的处理函数。我试图理解在这个例子中使用泛型所得到的东西??
switch (actionType)
{
case AddItem:
HandleAdd();
break;
case UpdateItem:
HandleUpdate();
break;
...
}
答案 0 :(得分:1)
Generic示例允许您动态添加处理程序(在运行时),而switch语句基本上是&#34;烘焙&#34;进入代码。
这是我能想出的原因的主要例子。
此外,通用示例看起来很花哨。
答案 1 :(得分:0)
在不知道使用场景的情况下很难判断哪种方法更好,但是在最初的示例中,您可以从数据库中提取和序列化数据,而无需为添加switch语句而烦恼每次你介绍一个新的动作。看起来通过使用泛型来节省开发时间。
我们还要检查使用此示例与switch语句相比的速度差异。如果您在函数调用时已准备好类型,则字典时间检索为O(1)。这与switch语句的检索相同,而不必为交换机烦恼。
答案 2 :(得分:0)
当您使用通用数据结构(字典)作为示例时,此问题与多态而非泛型有关。
正如您已经被告知的那样,切换是不好的,因为如果您想添加另一个案例,您必须修改这段代码。切换通常是代码气味,表明应该使用多态。
在这种情况下使用开关违反了开/关原则(SOLID)。简而言之,这个原则说,应该打开代码进行更改,但是关闭以进行修改。您提供的示例遵循此规则。如果您想要其他操作,则无需触摸此代码,只需添加另一个Task类即可。使用开关,您需要 MODIFY 现有代码。
我希望这有帮助!