Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/sql-server/22.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/fortran/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 泛型和数据库——设计问题_C#_Sql Server_Generics_Strong Typing - Fatal编程技术网

C# 泛型和数据库——设计问题

C# 泛型和数据库——设计问题,c#,sql-server,generics,strong-typing,C#,Sql Server,Generics,Strong Typing,现在的情况是,我有一个表来模拟一个实体。此实体具有多个属性(每个属性由表中的一列标识)。问题是,将来我需要添加新属性或删除一些属性。问题是如何对数据库和相应的代码进行建模(使用C#),以便在出现这种情况时,很容易“拥有”一个新属性 一开始只有一个属性,所以我有一个列。我用适当的类型和名称在类中定义了相应的属性,然后创建了存储过程来读取和更新它。然后是第二个属性,快速复制粘贴、更改名称和类型以及一些SQL,它就出现了。显然,这不是一个适合未来发展的模式。此时,你们中的一些人可能会建议使用ORM(E

现在的情况是,我有一个表来模拟一个实体。此实体具有多个属性(每个属性由表中的一列标识)。问题是,将来我需要添加新属性或删除一些属性。问题是如何对数据库和相应的代码进行建模(使用C#),以便在出现这种情况时,很容易“拥有”一个新属性

一开始只有一个属性,所以我有一个列。我用适当的类型和名称在类中定义了相应的属性,然后创建了存储过程来读取和更新它。然后是第二个属性,快速复制粘贴、更改名称和类型以及一些SQL,它就出现了。显然,这不是一个适合未来发展的模式。此时,你们中的一些人可能会建议使用ORM(EF或其他),因为这将自动生成SQL和代码,但目前这不是我的选择

我想只有一个过程来读取一个属性(按属性名称),另一个过程来更新它(按名称和值),然后是一些常规过程来读取同一语句中一个实体的一组或所有属性。如果你考虑使用泛型,但是数据库不知道泛型,所以不可能有强类型的解决方案。
我希望有一个“尽可能强类型化”的解决方案,这样我就不需要进行大量的转换和解析。我会在代码中定义可用的属性,这样您就不会猜测您有什么可用的属性,而是使用魔术字符串之类的东西。然后,在系统中添加新属性的过程只意味着在表中添加一个新列,并在代码中(例如在枚举中)添加一个新属性“定义”。

即使您说您不能使用它们,这也是大多数ORM所做的。根据您使用哪一个(或者如果是学习体验,甚至创建),它们的复杂性和性能会有很大差异。如果您喜欢重量轻的ORM,请检查。它还使用泛型,因此您可以检查代码,了解其工作原理,并在需要时创建自己的解决方案。

听起来您想这样做:

MyObj x = new MyObj();
x.SomeProperty = 10;
您已经为此创建了一个表,但您不希望在添加时继续更改该表

x.AnotherProperty = "Some String";
您需要像这样规范化表数据:

-> BaseTable
   RecordId, Col1, Col2, Col3

-> BaseTableProperty
   PropertyId, Name

-> BaseTableValue
   ValueId, RecordId, PropertyId, Value
你的班级看起来是这样的:

 public class MyObj
 {
      public int Id { get; set; }
      public int SomeProperty { get; set; }
      public string AnotherProperty { get; set; }
 }
从DL创建对象时,枚举记录集。然后编写一次代码,以与配置相同的名称检查属性(
BaseTableProperty.name
==
MyObj.
-然后在枚举记录集时尝试将类型转换为该类型

然后,您只需向对象添加另一个属性,在
BaseTableProperty
中向数据库添加另一条记录,然后就可以在
BaseTableValue
中存储该对象的值

例如:

 RecordId
 ========
 1

 PropertyId          Name
 ==========          ====
 1                   SomeProperty

 ValueId     RecordId       PropertyId      Value
 =======     ========       ==========      =====
 1           1              1               100
您有两个结果集,一个用于基本数据,另一个从属性和值表联接。当您枚举每个记录时,您会看到
SomeProperty
-是否存在
typeof(MyObj).GetProperty(“SomeProperty”)
存在?是吗?它的数据类型是什么?int?好的,然后尝试转换“100”通过设置属性来
int

 propertyInfo.SetValue(myNewObjInstance, Convert.ChangeType(dbValue, propertyInfo.PropertyType), null);

对于每个属性。

为什么你不能使用EF?微软的天才们已经在这方面为你找到了答案并做了很多工作。我不想看到你重新发明轮子。是的,我不明白你为什么需要避免ORM。(另外,我不知道C#泛型与这些有什么关系)我同意,但EF在体系结构方面有点落后,所以我现在还不能使用它。“落后一点”是什么意思?为什么你不能使用它?我提到泛型是因为我仍然需要一些强类型的“感觉”。当你调用
GetProperty(“PropertyName”)时
总是返回
Object
并没有多大帮助。我不想也不需要声明类中的每个属性。一次需要多个属性的情况很少发生。大多数情况下,我有对象ID,只需要知道其中一个属性。这就是为什么我要使用g通用的
GetProperty(int-objectID,string-propertyName)
方法。我接受这个方法,因为它最接近我将要采用的解决方案。