C#类继承自泛型集合的例子
作者:VinciYan
在C#中,除了泛型字典外,你还可以继承其他集合类型,本文通过实例代码主要介绍了C#类继承自泛型集合,需要的朋友可以参考下
继承自泛型字典的例子
这段代码定义了一个多层嵌套的字典结构,旨在组织和存储复杂的层级数据
using System; using System.Threading.Tasks; class Contract : Dictionary<string, Dictionary<string, Dictionary<string, string>>> { private readonly string type = "autodesk.data:exchange.contract.dynamo-1.0.0"; public Contract() { var contractContent = new Dictionary<string, Dictionary<string, string>> { { "contract", new Dictionary<string, string>() } }; Add(type, contractContent); } } class Program { static void Main() { // Create an instance of Contract var contract = new Contract(); // Access the outer dictionary using the predefined type key var typeKey = "autodesk.data:exchange.contract.dynamo-1.0.0"; // Check if the key exists and add data if (contract.TryGetValue(typeKey, out var contractContent)) { // Access the inner dictionary with the key "contract" if (contractContent.TryGetValue("contract", out var innerDictionary)) { // Add key-value pairs to the innermost dictionary innerDictionary["key1"] = "value1"; innerDictionary["key2"] = "value2"; // Retrieve and display values Console.WriteLine(innerDictionary["key1"]); // Outputs: value1 Console.WriteLine(innerDictionary["key2"]); // Outputs: value2 } } } }
value1 value2
再看一个Dynamo项目实例,这段代码的目的是创建一个嵌套字典结构,用于存储有关二进制引用组件的属性数据。使用接口IPropertySet作为多态机制的基础。通过嵌套字典结构实现多层次数据的组织和访问。提供灵活的属性管理,适合复杂对象的属性存储场景
using System; using System.Threading.Tasks; class BinaryReferenceComponent : Dictionary<string, Dictionary<string, IPropertySet>> { private string objectId = "autodesk.data:binary.reference.component-1.0.0"; public string ObjectId { get { return objectId; } } public BinaryReferenceComponent(string binaryId) { var propertyDictionary = new Dictionary<string, IPropertySet>(); propertyDictionary.Add("String", new StringPropertySet(binaryId)); propertyDictionary.Add("Uint32", new IntPropertySet()); this.Add("binary_reference", propertyDictionary); } } class StringPropertySet : IPropertySet { public string Id { get; set; } public string Revision { get; set; } public StringPropertySet(string binaryId, string revision = "v0") { Id = binaryId; Revision = revision; } } class IntPropertySet : IPropertySet { public int End { get; set; } public int Start { get; set; } public IntPropertySet(int start = 0, int end = 8710) { End = end; Start = start; } } interface IPropertySet { } class Program { static void Main() { // Create an instance of BinaryReferenceComponent with a binaryId var binaryReference = new BinaryReferenceComponent("exampleBinaryId"); // Access ObjectId Console.WriteLine($"ObjectId: {binaryReference.ObjectId}"); // Access properties of the component if (binaryReference.TryGetValue("binary_reference", out var propertySet)) { if (propertySet.TryGetValue("String", out var stringProperty)) { var stringProp = stringProperty as StringPropertySet; Console.WriteLine($"StringProperty Id: {stringProp.Id}, Revision: {stringProp.Revision}"); } if (propertySet.TryGetValue("Uint32", out var intProperty)) { var intProp = intProperty as IntPropertySet; Console.WriteLine($"IntProperty Start: {intProp.Start}, End: {intProp.End}"); } } } }
ObjectId: autodesk.data:binary.reference.component-1.0.0 StringProperty Id: exampleBinaryId, Revision: v0 IntProperty Start: 0, End: 8710
继承多种集合类型
在C#中,除了泛型字典外,你还可以继承其他集合类型,例如:
- List:可以创建自定义列表类,但不常见,建议使用组合
- HashSet:用于无重复元素集合,但继承并不常见
- Queue和Stack:分别用于队列和栈的实现
- Collection和ReadOnlyCollection:更适合继承,提供了更好的方法定制化能力
示例:继承 Collection
代码说明
CustomCollection<T>
类:- 继承自
Collection<T>
- 重写了
InsertItem
方法,添加插入前后的自定义行为 - 定义了一个
ItemAdded
事件,当新项目添加时触发
- 继承自
Main
函数:- 创建
CustomCollection<string>
的实例 - 订阅
ItemAdded
事件,输出添加的项信息 - 添加几个项目并显示集合中的所有项目
- 创建
关键点
- 事件处理: 使用事件机制通知项的添加
- 自定义行为: 通过重写方法实现特定逻辑
- 灵活性:
CustomCollection<T>
可以用于任何类型的集合
using System; using System.Collections.ObjectModel; class CustomCollection<T> : Collection<T> { // Event triggered when an item is added public event Action<T> ItemAdded; // Custom implementation of InsertItem protected override void InsertItem(int index, T item) { // Add custom behavior before inserting Console.WriteLine($"Inserting item at index {index}: {item}"); base.InsertItem(index, item); // Trigger the event after inserting ItemAdded?.Invoke(item); } // Method to display all items public void DisplayItems() { Console.WriteLine("Current items in collection:"); foreach (var item in this) { Console.WriteLine(item); } } } class Program { static void Main() { // Create an instance of CustomCollection var collection = new CustomCollection<string>(); // Subscribe to the ItemAdded event collection.ItemAdded += item => Console.WriteLine($"Item added: {item}"); // Add items to the collection collection.Add("Item1"); collection.Add("Item2"); collection.Add("Item3"); // Display all items in the collection collection.DisplayItems(); } }
运行结果:
Inserting item at index 0: Item1
Item added: Item1
Inserting item at index 1: Item2
Item added: Item2
Inserting item at index 2: Item3
Item added: Item3
Current items in collection:
Item1
Item2
Item3
注意
在C#中,类继承自泛型字典并不常见。以下是一些原因和建议:
原因
- 违背封装原则:直接继承集合类可能导致外部代码直接操作集合内部结构,违背封装原则
- 集合行为的复杂性:集合类提供的行为可能不完全适合自定义类的需求,可能需要重写大量方法。继承集合类可能引入维护复杂性
组合优于继承:常用的设计模式是组合,即在类内部包含一个集合,而不是继承它
建议
- 使用组合:在类中定义一个集合字段,并通过方法或属性操作它。这可以更好地控制访问和行为
扩展方法:如果需要对集合进行特定操作,可以使用扩展方法来增强其功能,而不是继承
将前面的一个继承的例子改为使用组合,运行结果不变
using System; using System.Collections.Generic; interface IPropertySet { } class StringPropertySet : IPropertySet { public string Id { get; set; } public string Revision { get; set; } public StringPropertySet(string binaryId, string revision = "v0") { Id = binaryId; Revision = revision; } } class IntPropertySet : IPropertySet { public int End { get; set; } public int Start { get; set; } public IntPropertySet(int start = 0, int end = 8710) { End = end; Start = start; } } class BinaryReferenceComponent { private Dictionary<string, Dictionary<string, IPropertySet>> properties = new(); public string ObjectId { get; } = "autodesk.data:binary.reference.component-1.0.0"; public BinaryReferenceComponent(string binaryId) { var propertyDictionary = new Dictionary<string, IPropertySet> { { "String", new StringPropertySet(binaryId) }, { "Uint32", new IntPropertySet() } }; properties.Add("binary_reference", propertyDictionary); } public Dictionary<string, IPropertySet> GetProperties(string key) { properties.TryGetValue(key, out var result); return result; } } class Program { static void Main() { // Create an instance of BinaryReferenceComponent var binaryReference = new BinaryReferenceComponent("exampleBinaryId"); // Access ObjectId Console.WriteLine($"ObjectId: {binaryReference.ObjectId}"); // Retrieve properties using GetProperties method var properties = binaryReference.GetProperties("binary_reference"); if (properties != null) { if (properties.TryGetValue("String", out var stringProperty)) { var stringProp = stringProperty as StringPropertySet; Console.WriteLine($"StringProperty Id: {stringProp.Id}, Revision: {stringProp.Revision}"); } if (properties.TryGetValue("Uint32", out var intProperty)) { var intProp = intProperty as IntPropertySet; Console.WriteLine($"IntProperty Start: {intProp.Start}, End: {intProp.End}"); } } else { Console.WriteLine("No properties found for the given key."); } } }
参考
到此这篇关于C#类继承自泛型集合的文章就介绍到这了,更多相关C#类继承自泛型集合内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!