繁体   English   中英

多种策略设计模式

[英]Multiple Strategy Design Pattern

我希望能够收集多个验证实体,它们都共享相同的接口。 这是我想出的:

public interface Ivalidateable
{
  bool IsValid(IValidateParam param);
}

public interface IValidateParam
{

}

public abstract EmployeeStrategy: Ivalidateable
{
  public abstract bool IsValid(User user); 
}

public abstract SpreadStrategy: IValidateable
{
 public abstract bool IsAvlid(Campaign campaign);
}

public class User: IValidateParam
{}

public class Campaign: IValidateParam
{}

public EmployeeTypeStragtegy: EmployeeStrategy, IValidateable
{
 public bool IsValid(User user)
 {
  if  (new[]{'e',a','b}.Contains(user.userId.first().toString()))
  return true;

  return false; 
 }
}

public TrailSpreadStrategy: SpreadStrategy, IValidateable
{
 public bool IsValid(Campaign campaign)
 {
  //logic goes here
 }
}

public EvenpreadStrategy: SpreadStrategy:, IValidateable
{
 public bool IsValid(Campaign campaign)
 {
  //logic goes here
 }
}

public class ValidationFactory
{
 private static List<IValidateable> stragtegies;

 static ValidationFactory
 {
  strategies = new List<IValidateable>();
  strategies.Add(new EmployeeTypeStragtegy());
  strategies.Add(new TrailSpreadStrategy());
 }

 public bool IsValid(//Need to pass User/Campaign)
 {
  //what do I do here?
 }
}

通过用户/广告系列的最佳方法是什么,以便我可以循环策略并检查IsValid?

这是我的处理方式:

// campaign object class, and it's separate validator logic

public class Campaign
{
}

public class CampaignValidator : IValidationStrategy<Campaign>
{
    public bool IsValid(Campaign test)
    {
        return true;
    }
}

// framework stuff

public interface IValidationStrategy<T>
{
    bool IsValid(T test);
}

public static class ValidationFactory
{
    private readonly static Dictionary<Type, object> _typeValidators;

    static ValidationFactory()
    {
        _typeValidators = new Dictionary<Type, object>();
        _typeValidators[typeof(Campaign)] = new CampaignValidator();
    }

    public static bool IsValid<T>(T obj)
    {
        return ((IValidationStrategy<T>)_typeValidators[typeof(T)]).IsValid(obj);
    }
}

之后,您可以调用ValidationFactory.IsValid(myObject); 并且如果类型在工厂静态构造函数中,它将给出true / false。

验证工厂正在做一种DI / IOC的事情,即您可以使用Ninject,Castle等来实现将类型映射到验证器类型。

您可以动态或不同地执行操作,而不必以相同的方式构建字典-查看验证程序实现的接口的泛型类型参数,或搜索基于IValidationStrategy<>的类,然后再次查看泛型类型参数。 但是以上是快速而简单的。

您是否有理由想要单独的验证器类?

我建议您看看FluentValidation的嵌套和集合验证功能。 如果您的策略包含对要与之一起验证的其他实体的引用,则此方法在没有额外的工厂和接口的情况下应该可以正常工作。

这个怎么样?

更改所有IsValid以使用此原型(用户,Campaign广告系列),例如:

public EmployeeTypeStragtegy: EmployeeStrategy, IValidateable
{
 public bool IsValid(User user, Campaign campaign)
 {
    return (new char[]{'e','a','b'}.Contains(user.userId.first().toString());
 }
}

然后通过适当的类型处理每个参数,这样它们都接受相同的参数。 接着:

public bool IsValid(User user, Campaign campaign)
 {
   bool valid;

   foreach (IValidateable iv in strategies)
   {
      if (!iv.IsValid(user, campaign))
          valid = false;
   }

   // This returns true if all are valid, false if not (not sure if this is the logic you expect)
   return valid;
 }

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM