Design patterns 策略规范模式中最显式的规范

Design patterns 策略规范模式中最显式的规范,design-patterns,factory-pattern,strategy-pattern,specification-pattern,Design Patterns,Factory Pattern,Strategy Pattern,Specification Pattern,比如说,我有很多业务逻辑来根据多个因素确定应用程序的行为。另外,我有一些非常好的地方,我知道我可以用策略模式来代替行为。另外,考虑到我正试图利用各种模式来解决一个问题 战略模式 规范模式 工厂模式 是否可以使用规范模式来确定工厂的策略,并保持开闭原则 我有一个工厂,我发现自己创建了switch语句,就像前面的代码一样,以选择正确的策略。这似乎适得其反 我想把所有这些逻辑决策都推到规范上,但接下来的问题是如何订购规范或首先选择最明确的规范 有没有办法解决这个问题?使用系统; using Sys

比如说,我有很多业务逻辑来根据多个因素确定应用程序的行为。另外,我有一些非常好的地方,我知道我可以用策略模式来代替行为。另外,考虑到我正试图利用各种模式来解决一个问题

  • 战略模式
  • 规范模式
  • 工厂模式
是否可以使用规范模式来确定工厂的策略,并保持开闭原则

我有一个工厂,我发现自己创建了switch语句,就像前面的代码一样,以选择正确的策略。这似乎适得其反

我想把所有这些逻辑决策都推到规范上,但接下来的问题是如何订购规范或首先选择最明确的规范

有没有办法解决这个问题?

使用系统;
using System;
using System.Collections.Generic;
using System.Linq;

using static BeyondOOP.Gender;

// having to make decisions based on logic
// control flow without all the nested if then
namespace BeyondOOP
{
    class Program
    {
        static void Main(string[] args)
        {
            var people = new List<Person>
            {
                new Person("Bill", new DateTime(1940, 10, 10), Male),
                new Person("Jill", new DateTime(1950, 10, 10), Female),
                new Person("Mary", new DateTime(2015, 10, 10), Female),
                new Person("Gary", new DateTime(1970, 10, 10), Male),
                new Person("Greg", new DateTime(1980, 10, 10), Male),
                new Person("Susan", new DateTime(2013, 10, 10), Female),
                new Person("Gabe", new DateTime(1999, 10, 10), Neutral),
                new Person("Barbie", new DateTime(2000, 10, 10), Female),
            };
            var greeter = new PersonGreeter();
            people.ForEach(greeter.Greet);
        }
    }

    // a little 'generics' flair
    // a 'predicate' is just a way
    // to predetermine true false
    interface IPredicate<T>
    {
        bool Matches(T value);
    }

    // this is just a simple DTO
    // Data transfer object, fancy for value container
    // it's just a way of passing values around
    class Person
    {
        public string Name { get; }
        public DateTime DateOfBirth { get; }
        public Gender Gender { get; }

        public Person(string name, DateTime dateOfBirth, Gender gender)
        {
            Name = name;
            DateOfBirth = dateOfBirth;
            Gender = gender;
        }
    }

    enum Gender { Male, Female, Neutral }

    // some prefabed predicates for 'Person'
    class OldManPredicate : IPredicate<Person>
    {
        public bool Matches(Person value) =>
            (DateTime.Now.Year - value.DateOfBirth.Year) >= 60 && 
                value.Gender == Gender.Male;
    }

    class MinorPredicate : IPredicate<Person>
    {
        public bool Matches(Person value) =>
            DateTime.Now.Year - value.DateOfBirth.Year < 18;
    }

    class ToddlerPredicate : IPredicate<Person>
    {
        public bool Matches(Person value) =>
            DateTime.Now.Year - value.DateOfBirth.Year > 2 &&
            DateTime.Now.Year - value.DateOfBirth.Year < 4;
    }

    class BabyPredicate : IPredicate<Person>
    {
        public bool Matches(Person value) =>
            DateTime.Now.Year - value.DateOfBirth.Year <= 2;
    }

    class TruePersonPredicate : IPredicate<Person>
    {
        public bool Matches(Person value) => true;
    }

    class GreetAction
    {
        public Func<Person,bool> Predicate { get; }
        public Func<Person,string> Messager { get; }

        public GreetAction(Func<Person, bool> predicate, 
            Func<Person, string> messager  )
        {
            Predicate = predicate;
            Messager = messager;
        }
    }
    class PersonGreeter
    {
        // someone may say that if you're using Func
        // why do you go through the trouble of the extra
        // classes. Predicate classes can be added freely
        // Only this factory class needs to be changed
        // and if I was to create a factory for the predicates 
        // and messagers then no changes would be neccessary
        private readonly List<GreetAction> _greetActions =
            new List<GreetAction>
            {
                // these have to be ordered
                // so they don't conflict or override
                // intended behavior
                // MinorPredicate is < 18 but babies and toddlers are also
                // less than 18, they need to preceed minors to work
                new GreetAction( new OldManPredicate().Matches, 
                    p => $"{p.Name}, you're getting up there!"),
                new GreetAction( new BabyPredicate().Matches,
                    p => $"{p.Name}, time to change the diaper!"),
                new GreetAction( new ToddlerPredicate().Matches,
                    p => $"{p.Name}, look, you're walking!"),
                new GreetAction( new MinorPredicate().Matches, 
                    p => $"{p.Name}, no, you may not have beer!"),
                // you need a default action
                // this is the same as a 'Null Pattern'
                new GreetAction( new TruePersonPredicate().Matches,
                    p => $"{p.Name}, hello there!"),
            }; 

        public void Greet(Person person) => 
            Console.WriteLine(_greetActions
                .First(p => p.Predicate(person))
                .Messager(person));
    }
}
使用System.Collections.Generic; 使用System.Linq; 使用静态BeyondOOP.Gender; //必须根据逻辑做出决定 //没有所有嵌套if-then的控制流 命名空间BeyondOOP { 班级计划 { 静态void Main(字符串[]参数) { var people=新列表 { 新人(“比尔”,新日期时间(1940,10,10),男性), 新人(“吉尔”,新约会时间(1950年10月10日),女性), 新人(“玛丽”,新约会时间(2015年10月10日),女性), 新人(“Gary”,新日期时间(1970年10月10日),男性), 新人(“格雷格”,新日期时间(1980年10月10日),男性), 新人(“苏珊”,新约会时间(2013年10月10日),女性), 新人(“Gabe”,新日期时间(1999年10月10日),中立, 新人(“芭比”,新日期时间(2000,10,10),女性), }; var greeter=new PersonGreeter(); people.ForEach(问候者,问候者); } } //有点“仿制药”的天赋 //“谓词”只是一种方式 //预知真假 接口IPredicate { bool匹配(T值); } //这只是一个简单的DTO //数据传输对象,用于值容器 //这只是一种传递价值观的方式 班主任 { 公共字符串名称{get;} public DateTime出生日期{get;} 公共性别{get;} 公共人物(字符串名称、出生日期时间、性别) { 名称=名称; 出生日期=出生日期; 性别=性别; } } 枚举性别{男性、女性、中性} //“Person”的一些预设谓词 类OldManPredicate:IPredicate { 公共布尔匹配(个人值)=> (DateTime.Now.Year-value.DateOfBirth.Year)>=60&& value.Gender==Gender.Male; } 类别MinorPredicate:IPredicate { 公共布尔匹配(个人值)=> DateTime.Now.Year-value.DateOfBirth.Year<18; } 学步班预告:I预告 { 公共布尔匹配(个人值)=> DateTime.Now.Year-value.DateOfBirth.Year>2&& DateTime.Now.Year-value.DateOfBirth.Year<4; } BabyPredicate类:IPredicate { 公共布尔匹配(个人值)=> DateTime.Now.Year-value.DateOfBirth.Year true; } 阶级贪婪 { 公共函数谓词{get;} 公共函数消息器{get;} 公共GreetAction(Func谓词, (函电) { 谓词=谓词; 送信人=送信人; } } 佩森格里特级 { //有人可能会说,如果您使用Func //你为什么要经历额外的麻烦 //谓词类可以自由添加 //只有此工厂类需要更改 //如果我要为谓词创建一个工厂 //而信息传递者则不需要任何改变 私有只读列表\u greetActions= 新名单 { //这些必须订购 //所以它们不会冲突或覆盖 //意向行为 //MinorPredicate年龄<18岁,但婴儿和学步儿童也有 //18岁以下,他们需要教育未成年人工作 新GreetAction(新的OldManPredicate()。匹配, p=>$“{p.Name},你正在爬上去!”, 新GreetAction(新的BabyPredicate()。匹配项, p=>$“{p.Name},该换尿布了!”), 新GreetAction(新的蹒跚学步预测()。匹配项, p=>$“{p.Name},看,你在走路!”, 新GreetAction(新的MinorPredicate()。匹配项, p=>$“{p.Name},不,你可能没有啤酒!”, //您需要一个默认操作 //这与“空模式”相同 新GreetAction(新TruePersonPredicate()。匹配, p=>$“{p.Name},你好!”), }; 公共无效问候语(人)=> 控制台。写入线(\u greetActions .First(p=>p.Predicate(person)) .信使(人); } }
如果您发布一些代码,那就太好了:)