java设计模式 -------- 行为模式 之 策略模式(2)

[本文是自己学习所做笔记,欢迎转载,但请注明出处:http://blog.csdn.net/jesson20121020]

  继续上节内容,还是以对各种类型的数组进行排序为例,这时,我们考虑复杂一点,如果,我们不再按照Cat的身高进行排序,我们想以Cat的年龄作为排序的依据,再如,我们不再按Dog的food进行排序,而是以Dog的体重作为依据进行排序,该怎么办呢,当然了,我们可以改动Cat类,Dog类,让其实现这些功能,但是,当类很多时,要改动每一个类,也是很麻烦的,也就是现在的这种结构不好实现。所以,我们希望我们能灵活的指定比较依据,所以,很容易想到,这要用到多态,我们可以定义一个比较器接口Comparator,然后,根据需要我们可以自定义每种类型的各种比较器如CatHeightComparator和CatWeightComparator都实现公共的比较器接口,最后,我们只需改动Cat类的compareTo()方法就行,具体实现如下:

Comparator.java

/**
 * 比较器
 * @author jesson
 *
 */
public interface Comparator {
	int compore(Object o1,Object o2);
}

CatHeightComparator.java

/**
 * Cat类型高度比较器
 *
 * @author jesson
 *
 */
public class CatHeightComparator implements Comparator {

	@Override
	public int compore(Object o1, Object o2) {
		// TODO Auto-generated method stub
		Cat c1 = (Cat) o1;
		Cat c2 = (Cat) o2;
		if (c1.getHeight() > c2.getHeight())
			return 1;
		else if (c1.getHeight() < c2.getHeight())
			return -1;
		else
			return 0;
	}

}

CatWeightComparator.java

/**
 * Cat类型重量比较器
 * @author jesson
 *
 */
public class CatWeightComparator implements Comparator {

	@Override
	public int compore(Object o1, Object o2) {
		// TODO Auto-generated method stub
		Cat c1 = (Cat) o1;
		Cat c2 = (Cat) o2;
		if (c1.getWeight() > c2.getWeight())
			return -1;
		else if (c1.getWeight() < c2.getWeight())
			return 1;
		else
			return 0;
	}

}

Comparable.java

/**
 * 可比较接口
 * 定义了一个比较方法
 * @author jesson
 *
 */
public interface Comparable {
	public int compareTo(Object o);
}

Cat.java

/**
 * Cat类 有属性身高,体重及toString()方法
 *
 * @author jesson
 *
 */
public class Cat implements Comparable {
	private int height; // 身高
	private int weight; // 体重

	//private Comparator comparator = new CatHeightComparator(); // 高度比较器
	private Comparator comparator = new CatWeightComparator(); // 重量比较器

	public Comparator getComparator() {
		return comparator;
	}

	public void setComparator(Comparator comparator) {
		this.comparator = comparator;
	}

	public Cat(int height, int weight) {
		// TODO Auto-generated constructor stub
		this.height = height;
		this.weight = weight;
	}

	public int getHeight() {
		return height;
	}

	public void setHeight(int height) {
		this.height = height;
	}

	public int getWeight() {
		return weight;
	}

	public void setWeight(int weight) {
		this.weight = weight;
	}

	/**
	 * 重写toString()方法
	 */
	@Override
	public String toString() {
		return this.getHeight() + "|" + this.getWeight();
	}

	/**
	 * 实现Comparable接口的compareTO方法
	 * 调用具体的比较器进行比较大小
	 */
	@Override
	public int compareTo(Object o) {
		return comparator.compore(this, o);
	}
}

DataSorter.java

/**
 * 排序类
 *
 * @author jesson
 *
 */
public class DataSorter {

	/**
	 * 冒泡排序方法
	 *
	 * @param Cat类型数组
	 */
	public static void bubbleSort(Object[] a) {
		for (int i = a.length - 1; i >= 1; i--) {
			for (int j = 0; j < i; j++) {
				Comparable o1 = (Comparable)a[j];
				Comparable o2 = (Comparable)a[j+1];
				if (o1.compareTo(o2) == 1) {
					swap(a, j, j + 1);
				}
			}
		}
	}

	/**
	 * 冒泡排序方法
	 *
	 * @param a
	 *            整数数组
	 */
	public static void bubbleSort(int[] a) {
		for (int i = a.length - 1; i >= 1; i--) {
			for (int j = 0; j < i; j++) {
				if (a[j] > a[j + 1]) {
					swap(a, j, j + 1);
				}
			}
		}
	}

	/**
	 * 交换两个数据
	 *
	 * @param a
	 *            Object类型数组
	 * @param x
	 *            数组下标1
	 * @param y
	 *            数组下标2
	 */
	private static void swap(Object[] a, int x, int y) {
		// TODO Auto-generated method stub
		Object temp = a[x];
		a[x] = a[y];
		a[y] = temp;
	}

	/**
	 * 交换两个数据
	 *
	 * @param a
	 *            数组
	 * @param x
	 *            数组下标1
	 * @param y
	 *            数组下标2
	 */
	private static void swap(int[] a, int x, int y) {
		// TODO Auto-generated method stub
		int temp = a[x];
		a[x] = a[y];
		a[y] = temp;
	}

	/**
	 * 打印数组
	 *
	 * @param a
	 *            Object类型数组
	 */
	public static void print(Object[] a) {
		for (int i = 0; i < a.length; i++)
			System.out.print(a[i] + " ");
		System.out.println();
	}

	/**
	 * 打印数组
	 *
	 * @param a
	 *            int类型数组
	 */
	public static void print(int[] a) {
		for (int i = 0; i < a.length; i++)
			System.out.print(a[i] + " ");
		System.out.println();
	}

}

Test.java

/**
 * 测试类
 * @author jesson
 *
 */
public class Test {
	public static void main(String[] args) {
		//int[] a = new int[]{9,8,2,4,5,6,7};
		Cat[] a = {new Cat(5,5),new Cat(1,1),new Cat(3,3)};
		//Dog[] a = {new Dog(3),new Dog(2),new Dog(6)};
		DataSorter.print(a);
		DataSorter.bubbleSort(a);
		DataSorter.print(a);
	}
}

   通过高度比较器和重量比较器,我们就可以灵活的选择比较的依据,这时,如果,需求再有变化,按照Cat的年龄进行排序时,只需要新建一个年龄比较器,然后为Cat类的Comparator的set方法或者Cat的构造方法传入新建的年龄比较器,这样不需再改动其他代码,就可以实现Cat类型的数组按新定义的年龄进行排序,最大限度地重用了代码。

时间: 2024-08-06 03:42:13

java设计模式 -------- 行为模式 之 策略模式(2)的相关文章

Java设计模式(七)策略模式 模板模式

(十三)策略模式 策略模式定义了多个封装起来的算法,封装的算法可以相互替换,并且算法的变化不会影响到使用算法的客户.借用另一位大神的例子. interface ICalculator{ public int calculate(String exp); } abstract class AbstractCalculator{ public int[] split(String exp,String opt){ String array[] = exp.split(opt); int arrayI

Java设计模式菜鸟系列(一)策略模式建模与实现

转载请注明出处:http://blog.csdn.net/lhy_ycu/article/details/39721563 今天开始咱们来谈谈Java设计模式.这里会结合uml图形来讲解,有对uml建模不熟的可以参考我的另一篇博文uml建模. 首先,个人觉得模式的设计就是一个将变化的东西和不变(稳定)的东西分离的过程.咱们的应用中可能有很多需要改变的地方,而模式要做的就是把它们"抽取"出来并进行"封装"和"实现",因此更多的时候咱们是面向接口编程

java设计模式(六)策略模式

策略模式定义了一系列的算法,并将每一个算法封装起来,而且使它们可以相互替换,让算法独立于使用它的客户而独立变化,具体应用场景如第三方支付对接不同银行的算法. 要点:1)抽象策略角色    2)具体策略角色:包装相关算法和行为 3)环境角色:持有一个策略类的引用,最终给客户端调用 1.抽象策略接口 public interface SwimmingStratege { public void swimming(); } 2.具体策略角色SwimmingWithFoot public class S

Java 设计模式学习笔记1——策略模式(Duck例子)

0.假设现有工程(Duck)中遇到为类添加功能的问题,如何设计类添加新的功能? 1.利用继承提供的Duck(鸭子)的行为会导致哪些缺点? (1)代码在多个子类中重复 (2)很多男知道所有鸭子的全部行为 (3)运行时的行为不容易改变 (4)改变会牵一发动全身,造成其他鸭子的不想要的改变 [设计原则] 找出应用中可能需要变化之处,把它们独立出来,不要和那些不需呀变化的代码混在一起 2.分开变化与不会变化的部分 将Duck分成两部分,鸭子类和鸭子行为. 类的固有属性和共用的方法写在类中,行为另起一个类

设计模式(行为型)之策略模式(Strategy Pattern)

PS一句:最终还是选择CSDN来整理发表这几年的知识点,该文章平行迁移到CSDN.因为CSDN也支持MarkDown语法了,牛逼啊! [工匠若水 http://blog.csdn.net/yanbober] 阅读前一篇<设计模式(行为型)之迭代器模式(Iterator Pattern)>http://blog.csdn.net/yanbober/article/details/45497881 概述 使用策略模式可以定义一些独立的类来封装不同的算法,每一个类封装一种具体的算法,在这里,每一个封

设计模式中的多态——策略模式详解

目录 1. 关于策略模式 2. 策略模式详解 2.1 策略模式定义 2.2 策略模式的UML类图 3.策略模式的优点 3.1 一个使用策略模式的例子 3.2 与其他实现方式的对比 3.3 使用策略模式的优点 4. 使用工厂方法模式改进原有策略模式 5. 总结 5. 参考资料 1. 关于策略模式 策略模式和java语言的多态特性有些像.java的多态特性允许我们面向接口编程,不用关心接口的具体实现.接口所指向的实现类,以及通过接口调用的方法的具体行为可以到运行时才绑定.这么做最大的好处是在尽可能实

设计模式——行为型模式之策略模式(二)

策略模式 在策略模式(Strategy Pattern)中,一个类的行为或其算法可以在运行时更改.这种类型的设计模式属于行为型模式. 在策略模式中,我们创建表示各种策略的对象和一个行为随着策略对象改变而改变的 context 对象.策略对象改变 context 对象的执行算法. 介绍 意图:定义一系列的算法,把它们一个个封装起来, 并且使它们可相互替换. 主要解决:在有多种算法相似的情况下,使用 if...else 所带来的复杂和难以维护. 何时使用:一个系统有许多许多类,而区分它们的只是他们直

Java设计模式(十) 备忘录模式 状态模式

(十九)备忘录模式 备忘录模式目的是保存一个对象的某个状态,在适当的时候恢复这个对象. class Memento{ private String value; public Memento(String value){ this.value = value; } public String getValue() { return value; } public void setValue(String value) { this.value = value; } } class Storage

【设计模式】简单工厂模式与策略模式

[前言]今天再次把<大话设计模式>一书拿出来翻了一下,对于前面一节初探中讲诉的简单工厂模式和策略模式,有了更好的理解.按照习惯,还是继续梳理梳理. [简单工厂模式]:封装(数据+算法) 简单工厂模式的特点: 每一个子类最好能做到职责单一,将每一个需要涉及的数据和算法,封装成一个独立的类. 工厂模式中的工厂类其实起到了一个调度者的角色: 2.1 工厂类可以达到将实现具体逻辑的子类隐藏的效果,只需要将自己暴露调用实例化的接口,根据工厂类提供的对外方法,在内部实现逻辑判断,并最后实例化具体的子类对象

Java设计模式(五)外观模式 桥梁模式

(九)外观模式 外观模式为子系统提供一个接口,便于使用.解决了类与类之间关系的,外观模式将类之间的关系放在一个 Facade 类中,降低了类类之间的耦合度,该模式不涉及接口. class CPU { public void startup(){ System.out.println("cpu start"); } public void shutdown(){ System.out.println("cpu stop"); } } class Memory { pu