使用命令设计模式添加新命令
Adding new commands with Command Design Pattern
我对 Command Design Pattern 感到进退两难。
Receiver 是 class 知道如何执行操作的接口。
在link中给出的例子中,接收者class Stock Trade
知道如何执行2个操作,StockTrade#buy
和StockTrade#sell
。这些操作对应于 2 个现有命令,BuyStockOrder
和 SellStockOrder
。
但是,如果需要添加其他命令怎么办,例如 FooStockOrder
和 BarStockOrder
?然后,必须更改 Receiver
接口(以及所有现有的实现),因此违反了开闭原则。
如何以 Receiver
(几乎)从未改变的方式解决该问题?
您忘记了您的 S.O.L.I.D principles, specifically Dependancy Inversion
不要以它特别期望具体实现的方式定义您的界面,例如 BuyStockOrder
或 SellStockOrder
。
宁可定义您的接口以期望像 CommandRequest
这样的抽象,然后您将发送 CommandRequest
的具体实现,而无需更改您的接口。
然后你的 Receiver
implimentation 可以决定如何处理它,当然正确的处理方法是使用 Strategy Pattern 但我会把它留给你。
这里有一些代码作为一个简单的例子:
public class Receiver : IReceiver
{
public CommandResult Process(CommandRequest request)
{
// Check the type of request and handle appropriately (or send to who can handle it)
return new Result();
}
}
public interface IReceiver
{
CommandResult Process(CommandRequest request);
}
public abstract class CommandResult
{
public bool Successful { get; set; }
}
public abstract class CommandRequest
{
}
public class Result : CommandResult
{
}
public class BuyStock : CommandRequest
{
public string Name { get; set; }
public decimal Value { get; set; }
}
public class SellStock : CommandRequest
{
public string Name { get; set; }
public decimal Value { get; set; }
}
internal class Program
{
private static void Main(string[] args)
{
var receiver = new Receiver();
var result = receiver.Process(new SellStock { Name = "PAYPL", Value = 100.20m });
Console.WriteLine(result.Successful ? "Yay!" : "Boo!");
}
}
我对 Command Design Pattern 感到进退两难。 Receiver 是 class 知道如何执行操作的接口。
在link中给出的例子中,接收者class Stock Trade
知道如何执行2个操作,StockTrade#buy
和StockTrade#sell
。这些操作对应于 2 个现有命令,BuyStockOrder
和 SellStockOrder
。
但是,如果需要添加其他命令怎么办,例如 FooStockOrder
和 BarStockOrder
?然后,必须更改 Receiver
接口(以及所有现有的实现),因此违反了开闭原则。
如何以 Receiver
(几乎)从未改变的方式解决该问题?
您忘记了您的 S.O.L.I.D principles, specifically Dependancy Inversion
不要以它特别期望具体实现的方式定义您的界面,例如 BuyStockOrder
或 SellStockOrder
。
宁可定义您的接口以期望像 CommandRequest
这样的抽象,然后您将发送 CommandRequest
的具体实现,而无需更改您的接口。
然后你的 Receiver
implimentation 可以决定如何处理它,当然正确的处理方法是使用 Strategy Pattern 但我会把它留给你。
这里有一些代码作为一个简单的例子:
public class Receiver : IReceiver
{
public CommandResult Process(CommandRequest request)
{
// Check the type of request and handle appropriately (or send to who can handle it)
return new Result();
}
}
public interface IReceiver
{
CommandResult Process(CommandRequest request);
}
public abstract class CommandResult
{
public bool Successful { get; set; }
}
public abstract class CommandRequest
{
}
public class Result : CommandResult
{
}
public class BuyStock : CommandRequest
{
public string Name { get; set; }
public decimal Value { get; set; }
}
public class SellStock : CommandRequest
{
public string Name { get; set; }
public decimal Value { get; set; }
}
internal class Program
{
private static void Main(string[] args)
{
var receiver = new Receiver();
var result = receiver.Process(new SellStock { Name = "PAYPL", Value = 100.20m });
Console.WriteLine(result.Successful ? "Yay!" : "Boo!");
}
}