
一 概要说明
命令模式
意图(Intent):
将一个请求封装为一个对象,从而使你可用不同的请求对函数进行参数化;
对请求排队或记录请求日志,以及支持可撤消的操作。
个人观点:把函数用一个对象封装起来,使其可被别人拿走,想什么时候用就什么时候用。
策略模式
意图:
定义一系统的算法,把它们一个个封装起来,并且使它们可相互替换。
本模式使得算法可独立于使用它的客户而变化。
个人观点:把函数用一个对象封装起来,可以通过换这个封装的不同状态换算法。
总结
通过上面的定义可以看出来吧,他俩的共性都是把,函数变成了对象。
一个侧重点在时间维度上,一个侧重可多态的换算法。
我的理解:就是把函数封装成对象的目的不同。做法一样,目的不同。
下面我用坦克大战颜色一下他们的作用之争。
当前:抽象工厂
需求:坦克大战
创建两种坦克
| 坦克类型 | 射程 | 速度 |
| b70 | 70米 | 时/70公里 |
| b50 | 50米 | 时/70公里 |
关联知识
策略模式和职责链模式实现坦克大战3_策略结合职责链-优快云博客
二 第一战
命令模式代码
import java.util.ArrayList;
//级别功能类
class Function{
final static String mShot = "射击:";
static void shot70() {
System.out.println(mShot+"70");
}
static void shot50() {
System.out.println(mShot+"50");
}
}
//---接口----------------------------------
//命令接口
interface ICommand{
void execute();
}
//坦克接口
interface Itank{
void exe();
}
//---实现-----------------------------------------
//命令实现-70功能
class B70Command implements ICommand{
public void execute() {
Function.shot70();
}
}
//命令实现-50功能
class B50Command implements ICommand{
public void execute() {
Function.shot50();
}
}
//坦克基类
abstract class Tank implements Itank{
ICommand mCommand;
public void exe() {
mCommand.execute();
}
}
//坦克实现-70坦克
class B70Tank extends Tank{
public B70Tank() {
mCommand = new B70Command();
}
}
//坦克实现-50坦克
class B50Tank extends Tank{
public B50Tank() {
mCommand = new B70Command();
}
}
//--调用段---------------------------------------------------
public class Client {
public static void main(String[] args) {
System.out.println("hello world !");
B70Tank b70 = new B70Tank();
b70.exe();
}
}
运行结果
![]()
策略模式
代码
import java.util.ArrayList;
//功能基类
class Function{
final static String mShot = "射击:";
static void shot70() {
System.out.println(mShot+"70");
}
static void shot50() {
System.out.println(mShot+"50");
}
}
//--接口--------------------------------------------------------------
// interface
interface IStrategy{
void execute();
}
interface Itank{
void exe();
}
// 坦克基类
abstract class Tank implements Itank{
//策略接口
IStrategy mStrategy;
public void exe() {
mStrategy.execute();
}
}
//-------Concrete 具体实现--------------------------------------------------
//70策略实现
class B70Strategy implements IStrategy{
public void execute() {
Function.shot70();
}
}
// 50策略实现
class B50Strategy implements IStrategy{
public void execute() {
Function.shot50();
}
}
// 70坦克实现-装载70策略
class B70Tank extends Tank{
public B70Tank() {
mStrategy = new B70Strategy();
}
}
// 50坦克实现-装载50策略
class B50Tank extends Tank{
public B50Tank() {
mStrategy = new B50Strategy();
}
}
//--- Client 调用端----------------------------------------------------
public class Client {
public static void main(String[] args) {
System.out.println("hello world !");
B70Tank b70 = new B70Tank();
b70.exe();
}
}
![]()
评判结果:完全看不出差别。
看来是我的示例有问题,开始第二回合吧
三 第二战(用多线程,看看怎么样,这应该是命令模式的优势项目)
命令模式代码
//功能基础类
import java.util.ArrayList;
class Function{
final static String mShot = "射击:";
static void shot70() {
System.out.println(mShot+"70");
}
static void shot50() {
System.out.println(mShot+"50");
}
}
//---接口层---------------------------------------------------------
interface ICommand{
void execute();
}
interface Itank{
void exe();
}
//---实现层---------------------------------------------------------------------
class B70Command implements ICommand{
public void execute() {
Function.shot70();
}
}
class B50Command implements ICommand{
public void execute() {
Function.shot50();
}
}
//抽象坦克
abstract class Tank implements Itank{
ICommand mCommand;
ArrayList<ICommand> mList = new ArrayList<ICommand>();
public ArrayList<ICommand> getmList() {
return mList;
}
public void exe() {
//mCommand.execute();
mList.add(mCommand);
}
}
//70坦克-装载70坦克命令
class B70Tank extends Tank{
public B70Tank() {
mCommand = new B70Command();
}
}
//50坦克-装载50坦克命令
class B50Tank extends Tank{
public B50Tank() {
mCommand = new B50Command();
}
}
//线程类
class MyThread extends Thread{
ArrayList<ICommand> mList;
public MyThread(ArrayList<ICommand> list) {
mList = list;
}
public void run() {
System.out.println("MyThread run");
while(true) {
for(ICommand com:mList) {
//执行完,直接删除对象
com.execute();
mList.remove(com);
break;
}
}
}
}
//--客户端----------------------------------------------------------------------------
//客户端调用
public class Client {
public static void main(String[] args) {
System.out.println("hello world !");
B70Tank b70 = new B70Tank();
MyThread t = new MyThread(b70.getmList());
t.start();
//每执行一次就将命令压入线程队列
b70.exe();
try {
t.sleep(500);
}catch(Exception e) {
}
t.stop();
}
}
运行结果

策略模式代码
//功能基础类
import java.util.ArrayList;
class Function{
final static String mShot = "射击:";
static void shot70() {
System.out.println(mShot+"70");
}
static void shot50() {
System.out.println(mShot+"50");
}
}
//--接口层----------------------------------------------------------------------------
//策略接口
interface IStrategy{
void execute();
}
//坦克接口
interface Itank{
void exe();
}
//--实现层----------------------------------------------------------------------------
//策略实现-70
class B70Strategy implements IStrategy{
public void execute() {
Function.shot70();
}
}
class B50Strategy implements IStrategy{
public void execute() {
Function.shot50();
}
}
abstract class Tank implements Itank{
IStrategy mStrategy;
ArrayList<IStrategy> mList = new ArrayList<IStrategy>();
public ArrayList<IStrategy> getmList() {
return mList;
}
public void exe() {
//mCommand.execute();
mList.add(mStrategy);
}
}
class B70Tank extends Tank{
public B70Tank() {
mStrategy = new B70Strategy();
}
}
class B50Tank extends Tank{
public B50Tank() {
mStrategy = new B50Strategy();
}
}
class MyThread extends Thread{
ArrayList<IStrategy> mList;
public MyThread(ArrayList<IStrategy> list) {
mList = list;
}
public void run() {
System.out.println("MyThread run");
while(true) {
for(IStrategy com:mList) {
com.execute();
mList.remove(com);
break;
}
}
}
}
//-- 测试端 ---------------------------------------------------------------------------
public class Client {
public static void main(String[] args) {
System.out.println("hello world !");
B70Tank b70 = new B70Tank();
MyThread t = new MyThread(b70.getmList());
t.start();
b70.exe();
try {
t.sleep(500);
}catch(Exception e) {
}
t.stop();
}
}
运行结果

第二战 评判结果
又没分除胜负,为什么呢?
因为在坦克看来,无论桥接的是命令还是策略。都是一样的。
而他们俩的真正差别在于命令和策略的来源。
在坦克看来,都是策略。
差别在于,命令模式,是把一个Service类变成了策略。
这才是他们真正的差别。
不争了,命令本身就是一种特殊的策略。
命令是把一个Service的接口,适配成了策略。
策略是啥,是一个函数的多态。
命令呢也是,只不过他是把本来不是接口的一些函数作为接口,变了策略的方式提供给了调用端。
命令就是一种特殊的策略。
命令=策略+适配器
761

被折叠的 条评论
为什么被折叠?



