如果Dictionary键可能是一个不同的类型,我怎么能使这个代码更通用,这取决于库的用户想要实现什么?例如,有人可能在使用“唯一键”的情况下使用扩展方法/接口,可以说节点实际上是“int”而不是“字符串”。
public interface ITopology
{
Dictionary<string, INode> Nodes { get; set; }
}
public static class TopologyExtns
{
public static void AddNode(this ITopology topIf, INode node)
{
topIf.Nodes.Add(node.Name, node);
}
public static INode FindNode(this ITopology topIf, string searchStr)
{
return topIf.Nodes[searchStr];
}
}
public class TopologyImp : ITopology
{
public Dictionary<string, INode> Nodes { get; set; }
public TopologyImp()
{
Nodes = new Dictionary<string, INode>();
}
}
答案 0 :(得分:6)
使界面通用,然后使用Func<INode,T>
作为密钥的选择器。这假定您希望从节点中提取字典的键。如果这不是一个硬性要求,那么您可以使用签名中的泛型类型说明符指定密钥本身。
public interface ITopology<T>
{
Dictionary<T, INode> Nodes { get; set; }
}
public static class TopologyExtns
{
public static void AddNode<T>(this ITopology<T> topIf, INode node, Func<INode,T> keySelector )
{
topIf.Nodes.Add( keySelector(node), node );
}
public static INode FindNode<T>(this ITopology<T> topIf, T searchKey )
{
return topIf.Nodes[searchKey];
}
}
public class TopologyImp<T> : ITopology<T>
{
public Dictionary<T, INode> Nodes { get; set; }
public TopologyImp()
{
Nodes = new Dictionary<T, INode>();
}
}
您可能还会考虑将INode设为通用类型。这将允许您将Key指定为泛型类型的属性,该实现可以遵循相应的“真实”键。这样可以避免为扩展方法提供密钥或选择器。
替代:
public interface INode<T>
{
T Key { get; }
string Name { get; set; }
int ID { get; set; }
}
public class StringNode : INode<string>
{
public string Key { get { return this.Name; } }
public string Name { get; set; }
public int ID { get; set; }
}
public interface ITopology<T>
{
Dictionary<T, INode<T>> Nodes { get; set; }
}
public static class TopologyExtns
{
public static void AddNode<T>(this ITopology<T> topIf, INode<T> node )
{
topIf.Nodes.Add( node.Key, node );
}
public static INode<T> FindNode<T>(this ITopology<T> topIf, T searchKey )
{
return topIf.Nodes[searchKey];
}
}
public class TopologyImp<T> : ITopology<T>
{
public Dictionary<T, INode<T>> Nodes { get; set; }
public TopologyImp()
{
Nodes = new Dictionary<T, INode<T>>();
}
}
用作:
var topology = new TopologyImp<string>();
topology.AddNode( new StringNode { Name = "A", ID = 0 } );
var node = topology.FindNode( "A" );
答案 1 :(得分:2)
public interface ITopology<T>
{
Dictionary<T, INode> Nodes { get; set; }
}
public static class TopologyExtns<T>
{
public static void AddNode<T>(this ITopology<T> topIf, T key, INode node)
{
topIf.Nodes.Add(key, node);
}
public static INode FindNode<T>(this ITopology<T> topIf, T searchKey)
{
return topIf.Nodes[searchKey];
}
}
public class TopologyImp<T> : ITopology<T>
{
public Dictionary<T, INode> Nodes { get; set; }
public TopologyImp()
{
Nodes = new Dictionary<T, INode>();
}
}
答案 2 :(得分:2)
为什么不将拓扑界面设为通用?我自己对扩展方法有点模糊,但这应该是可行的。
public interface ITopology<TKey>
{
Dictionary<TKey, INode> Nodes { get; set; }
}
public static class TopologyExtns
{
public static void AddNode<T>(this ITopology<T> topIf, T key, INode node)
{
topIf.Nodes.Add(key, node);
}
public static INode FindNode<T>(this ITopology<T> topIf, T searchObj)
{
return topIf.Nodes[searchObj];
}
}
public class TopologyImp : ITopology<String>
{
public TopologyImp()
{
Nodes = new Dictionary<String, INode>();
}
}