如何在 C# 扩展中 return sub 类?
How to return sub classes in c# extensions?
我有这个扩展方法。
public static List<Framework.Model> FetchAll(this Framework.Model model)
{
List<Framework.Model> models = new List<Framework.Model>();
StringBuilder Fields = new StringBuilder();
var properties = GetProperties(model);
foreach (var p in properties)
{
if (!p.Name.Equals("Table"))
Fields.Append(p.Name + ",");
}
Fields.Length--;
System.Data.DataTable data = (System.Data.DataTable)engine.RunDataTable("select " + Fields.ToString() + " from " + model.Table + ";").Data;
foreach (System.Data.DataRow rw in data.Rows)
{
foreach (System.Data.DataColumn col in data.Columns)
{
foreach (var p in properties)
{
if (col.ColumnName.Equals(p.Name))
{
if (p.PropertyType == typeof(DateTime?))
{
p.SetValue(model, DateTime.Parse(rw[col.ColumnName].ToString()));
}
else
{
p.SetValue(model, Convert.ChangeType(rw[col.ColumnName], p.PropertyType));
}
}
}
}
models.Add(model);
}
return models;
}
我有这个基础class。
public interface Model
{
string Table { get; set; }
}
我也有这个子class。
public class Department : Framework.Model
{
public Department()
{
this.Table = "departments";
}
public int Dbid { get; set; }
public string Code { get; set; }
public DateTime? created_at { get; set; }
public DateTime? updated_at { get; set; }
public string Table
{
get; set;
}
}
我现在尝试使用上面的扩展方法。
List<Model.Department> depts = new List<Model.Department>();
depts = new Model.Department().FetchAll();
但这是一个编译器错误,因为它无法将基数 class 转换为子 class。
我的问题只是如何 return 一个子 class 因为我想要的只是当我调用扩展方法时它将 return 数据库中那个特定 table 上的所有数据这是我的 sub class 所以我想获取 sub classes.
的列表
顺便说一下,扩展方法是我希望它能够灵活地接受不同的子classes,这就是我以这种方式构建它的原因。
您想创建一个通用扩展方法,constraint 为 Framework.Model
:
public static List<T> FetchAll(this T model) where T:Framework.Model
{
List<T> models = new List<T>();
//...
return models;
}
*未经测试的代码
很简单。您只需要使其通用即可。
public static List<T> FetchAll<T>(this T model) where T: Framework.Model
{
List<T> models = new List<T>();
...
foreach (System.Data.DataRow rw in data.Rows)
{
<... modifying model's properties ...>
models.Add(model);
}
...
return models;
}
之后你甚至不需要指定泛型类型——编译器会从你的代码中推断出来:
var depts = new Model.Department().FetchAll();
// depts is List<Model.Department> if you've built class hierarchy correctly
但是,您的代码还有一个问题。让我们看一下上面的循环。您试图一次又一次地将相同的对象添加到列表中。由于您正在修改对象的属性,因此您最终会得到对同一对象的 N 个引用的列表,其中包含您从数据库中获取的 table 最后一行的属性。我不相信这是你真正需要的,但我实际上并没有得到你真正需要的东西,所以除非你澄清它,否则不能真正提出任何建议。
我有这个扩展方法。
public static List<Framework.Model> FetchAll(this Framework.Model model)
{
List<Framework.Model> models = new List<Framework.Model>();
StringBuilder Fields = new StringBuilder();
var properties = GetProperties(model);
foreach (var p in properties)
{
if (!p.Name.Equals("Table"))
Fields.Append(p.Name + ",");
}
Fields.Length--;
System.Data.DataTable data = (System.Data.DataTable)engine.RunDataTable("select " + Fields.ToString() + " from " + model.Table + ";").Data;
foreach (System.Data.DataRow rw in data.Rows)
{
foreach (System.Data.DataColumn col in data.Columns)
{
foreach (var p in properties)
{
if (col.ColumnName.Equals(p.Name))
{
if (p.PropertyType == typeof(DateTime?))
{
p.SetValue(model, DateTime.Parse(rw[col.ColumnName].ToString()));
}
else
{
p.SetValue(model, Convert.ChangeType(rw[col.ColumnName], p.PropertyType));
}
}
}
}
models.Add(model);
}
return models;
}
我有这个基础class。
public interface Model
{
string Table { get; set; }
}
我也有这个子class。
public class Department : Framework.Model
{
public Department()
{
this.Table = "departments";
}
public int Dbid { get; set; }
public string Code { get; set; }
public DateTime? created_at { get; set; }
public DateTime? updated_at { get; set; }
public string Table
{
get; set;
}
}
我现在尝试使用上面的扩展方法。
List<Model.Department> depts = new List<Model.Department>();
depts = new Model.Department().FetchAll();
但这是一个编译器错误,因为它无法将基数 class 转换为子 class。 我的问题只是如何 return 一个子 class 因为我想要的只是当我调用扩展方法时它将 return 数据库中那个特定 table 上的所有数据这是我的 sub class 所以我想获取 sub classes.
的列表顺便说一下,扩展方法是我希望它能够灵活地接受不同的子classes,这就是我以这种方式构建它的原因。
您想创建一个通用扩展方法,constraint 为 Framework.Model
:
public static List<T> FetchAll(this T model) where T:Framework.Model
{
List<T> models = new List<T>();
//...
return models;
}
*未经测试的代码
很简单。您只需要使其通用即可。
public static List<T> FetchAll<T>(this T model) where T: Framework.Model
{
List<T> models = new List<T>();
...
foreach (System.Data.DataRow rw in data.Rows)
{
<... modifying model's properties ...>
models.Add(model);
}
...
return models;
}
之后你甚至不需要指定泛型类型——编译器会从你的代码中推断出来:
var depts = new Model.Department().FetchAll();
// depts is List<Model.Department> if you've built class hierarchy correctly
但是,您的代码还有一个问题。让我们看一下上面的循环。您试图一次又一次地将相同的对象添加到列表中。由于您正在修改对象的属性,因此您最终会得到对同一对象的 N 个引用的列表,其中包含您从数据库中获取的 table 最后一行的属性。我不相信这是你真正需要的,但我实际上并没有得到你真正需要的东西,所以除非你澄清它,否则不能真正提出任何建议。