Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/271.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#_Oop_Solid Principles - Fatal编程技术网

C# 扩展基类以包含详细信息?

C# 扩展基类以包含详细信息?,c#,oop,solid-principles,C#,Oop,Solid Principles,我的DAL已经返回了一个DTO。比如说 public class CustomerDTO { public int CustId {get; set; } public int CustType {get; set; } . . . public string GetCustomerTypes{ get { if (CustType== 1) return "Special Customer";

我的DAL已经返回了一个DTO。比如说

public class CustomerDTO
{
    public int CustId {get; set; }
    public int CustType {get; set; }
    .
    . 
    .
    public string GetCustomerTypes{
      get {  if (CustType== 1) 
               return "Special Customer";
             else if(CustType==
}
现在,我的类中有多个属性,它们没有与任何表链接&只是表示一些属性的代码,比如我可以拥有的CustId(1='Special Customer',2='Defaulter'或3='New Customer')。现在我需要在DTO上显示它们的属性

我可以像上面所做的那样,将业务逻辑嵌入到SQL语句或DTO类中。然而,对于不同的列,我最终得到了很多条件逻辑。另外,如果我做另一个DTO,这个条件逻辑会再次重复


如何在我的类设计中封装此逻辑并避免重复?

您可以使类成为部分类,并在部分类中编写额外的逻辑。如果它对所有DTO都是通用的,那么可以将该额外逻辑放在基类中,并在为DTO创建的所有分部类中继承它

至于将类型“转换”为字符串的问题,只需定义Enum CustomerType并为每个值在自定义属性中设置所需的文本。这样,您将拥有的通用逻辑是返回每个实体中的Type属性的属性值

大概是这样的:

因此,对于您的示例,我将定义一个枚举:

public enum CustomerType
{
[Tag("SpecialCustomer")]
SpecialCustomer = 1,
...
}
然后在分部类中(如果Entities是生成的代码),我会将默认成员包装到一个属性中,如下所示:

public string CustomerTypeAsString
{
 get
    { 
        return GetTagValue(CustType);
    }
}

我建议您将这些值放入数据库中。您可以构建单独的表,如:

CREATE TABLE CustomerTypes (
    ID INT PRIMARY KEY IDENTITY(1, 1),
    Name VARCHAR(50) NOT NULL
)
或者,您可以构建一个包含类型代码的表,如:

CREATE TABLE ListTypes (
    ID INT PRIMARY KEY IDENTITY(1, 1),
    Name VARCHAR(50) NOT NULL,
    TypeCode CHAR(2) NOT NULL
)
无论哪种方式,当您从数据库收集DTO时,都要连接到这些表并获取该值。因此,如果构建一个表,它可能看起来像:

SELECT c.*, ct.Name FROM Customer c
    JOIN CustomerTypes ct ON ct.ID = c.CustType
如果将更通用的表与类型代码一起使用,它可能如下所示:

SELECT c.*, lt.Name FROM Customer c
    JOIN ListTypes lt ON lt.ID = c.CustType AND lt.TypeCode = '01'
static class DtoHelper {
    public static string GetCustomerType(int type) {
        ... // Custom logic goes here
    }
}

这种方法之所以对您如此有效,是因为您需要字符串值,但仅用于显示目的,而且在以后的许多类型中都需要它。此外,您已经在数据库中获取了实体,所以让数据库来完成这项工作。最后,如果希望在组合框中列出这些值并让用户选择它们,可以从数据库绑定该组合框,而不是静态绑定


但简而言之,这使您的应用程序更易于修改和扩展。

如果某个逻辑重复,您应该将其放在单独的方法中。方法的位置取决于系统的结构,但通常有三个主要选项:

  • 将逻辑放入helper类中
  • 将逻辑放入基类
  • 将逻辑放入扩展方法中
第一个选项是最简单的,并且需要最少的修改:只需添加一个带有静态方法的类,如下所示:

SELECT c.*, lt.Name FROM Customer c
    JOIN ListTypes lt ON lt.ID = c.CustType AND lt.TypeCode = '01'
static class DtoHelper {
    public static string GetCustomerType(int type) {
        ... // Custom logic goes here
    }
}
第二种方法灵活性最低,因为它要求DTO继承一个公共类:

class WithCustomerType {
    private int custType;
    public string CustomerType {
        get {
            ... // Custom logic goes here
        }
    }
}
public class CustomerDTO : WithCustomerType {
    ...
}
第三个选项更灵活,因为它使用接口而不是类型:

interface IWithRawCustomerType {
    int RawCustomerType {get;}
}
static class DtoExtensions {
    public static string GetCustomerType(this IWithRawCustomerType dto) {
        int type = dto.RawCustomerType;
        ...
    }
}
class CustomerDTO : IWithRawCustomerType {
    ...
}

那么扩展方法呢

 public static  class DerivedValues
 {
     public static void ToCustomerTypes(this CustomerDTO dto)
     {
             if (dto.CustType == 1)
             dto.GetCustomerTypes = "Special Customer";
     }
 }
主要用途

var c1 = new CustomerDTO();
        c1.ToCustomerTypes();

嗨,迈克尔,谢谢你的回复。这对我的报道也有帮助!我可以这样做,但是我必须请求DBA,因为它是一个内置数据库。你能建议通过类设计来实现这一点吗?@DamienJoe,你是说你不能通过DBA来实现这一点,还是说你正在寻找另一个选项,以防他们不这么做?嗨,Michael,我的表上大约有15个字段是这样的。大多数设置为2到3个值。我正在请求另一个选项,以防DBA拒绝整个想法。如果您正在寻找另一个选项,请使用@dasblinkenlight提供的选项-如果可以,请使用第三个选项-这是一个极好的答案!你知道,我从来没有考虑过在代码中做这样的事情,因为它感觉像是一个数据库操作。将列表放入数据库也有助于在组合框中报告和列出这些列表。然而,对于你的第三种方法,我非常喜欢。妙极了!