北邮JAVA高级语言程序设计(选修课)设计模式大作业

北邮JAVA高级语言程序设计(选修课)设计模式大作业

题目描述:
设计模式一(单子、工厂、策略模式)练习
1. 假设现在要设计一个贩卖各类书籍的电子商务网站的购物车系统。对所有的教材类图书 实行每本一元的折扣;对连环画类图书提供每本7%的促销折扣;而对非教材类的计算机图书有3%的折扣;对其余书没有折扣。使用策略模式、工厂模式、单子模式进行设计,类图如下。

类图说明:

北邮JAVA高级语言程序设计(选修课)设计模式大作业_第1张图片Sale:代表依次销售。getTotal方法用于返回本次销售的优惠后总价。
SaleLineItem:代表一个销售项目。1次销售会对应多个销售项目。如顾客总共购买了2本《UML与模式应用》,3本《Java与模式》,则对应需要创建两个SaleLineItem对象,1个对应的是2本《UML与模式应用》的购买,1个对应的是3本《Java与模式》的购买。
ProductSpecification:书的描述信息,包括书的isbn号、书名、单价和书的类型。书的类型包括:非教材类的计算机图书、教材类图书、连环画类图书、其他共4种。在本例中共有5种书(见后面描述),因此需要创建5个ProductSpecification对象。
PricingStrategyFactory:策略工厂,负责根据书的类型提供对应的策略类,策略类将根据具体的优惠策略计算折扣后1个销售项目(SaleLineItem)的总价。要求:该策略工厂要设计成单子。
IPricingStrategy:策略类的接口,用于向SaleLineItem屏蔽具体的策略类。
FlatRateStrategy:按每本优惠x元的策略。
PercentageStrategy:按百分比进行优惠的策略。
NoDiscountStrategy:不进行优惠的策略。思考:为什么要设计这个类?如果没有这个类,会引发什么问题?
要求:设计中要考虑优惠的比例(如每本优惠1元、7%、3%)会发生变化?在设计时要考虑到这种变化,使得变化到来时,对现有代码的影响尽量小。
注意:本例中,策略是应用于1个SaleLineItem对象,而不是应用于Sale对象,为什么?

请用Java语言实现上述每一个类,并书写测试类,实现下述场景:
一次购物,购买了2本教材类图书《UML与模式应用》,单价是18元/本;购买了2本非教材类的计算机图书《Java与模式》,单价是34元/本;购买了1本非教材类的计算机图书《HeadFirst 设计模式》,单价是58元/本;购买了3本连环画类图书《爱丽丝历险记》,单价是30元/本;购买了1本其他类图书《煲汤大全》,单价是20元/本。请计算出本次购物优惠后价格。

源代码:

import java.util.ArrayList;
import java.util.Iterator;

public class TestClass {
	public static void mian(String[] args)
	{

		ProductSpecification p1 = new ProductSpecification("00001","UML与模式应用",18,"A");
		ProductSpecification p2 = new ProductSpecification("00001","Java与模式",34,"C");
		ProductSpecification p3 = new ProductSpecification("00003","HeadFirst设计模式",58,"C");
		ProductSpecification p4 = new ProductSpecification("00004","爱丽丝历险记",30,"B");
		ProductSpecification p5 = new ProductSpecification("00005","煲汤大全",20,"D");
		PricingStrategyFactory factor = PricingStrategyFactory.getInstance();
		SaleLineItem item1 = new SaleLineItem(2,p1,factor.getPricingStrategy(p1.getType()));
		SaleLineItem item2 = new SaleLineItem(2,p2,factor.getPricingStrategy(p2.getType()));
		SaleLineItem item3 = new SaleLineItem(1,p3,factor.getPricingStrategy(p3.getType()));
		SaleLineItem item4 = new SaleLineItem(3,p4,factor.getPricingStrategy(p4.getType()));
		SaleLineItem item5 = new SaleLineItem(1,p5,factor.getPricingStrategy(p5.getType()));
		Sale s = new Sale();
		s.addItem(item1);
		s.addItem(item2);
		s.addItem(item3);
		s.addItem(item4);
		s.addItem(item5);
		System.out.println("The total price is:"+String.format("%.2f",s.getTotal()));
	}
}

//书的描述信息,包括书的isbn号、书名、单价和书的类型
class ProductSpecification
{
	String ISBN;
	String Name;
	double Price;
	String Type;
	
	public ProductSpecification(String ISBN, String Name, double Price ,String Type) 
	{
		this.ISBN = ISBN;
		this.Name = Name;
		this.Price =Price;
		this.Type = Type;
	}
	public String getISBN() 
	{
		return ISBN;
	}
	public String getName()
	{
		return Name;
	}
	public double getPrice() 
	{
		return Price;
	}
	public String getType() 
	{
		return Type;
	}
}

//根据具体的优惠策略计算折扣后1个销售项目(SaleLineItem)的总价
class PricingStrategyFactory
{
	 private static PricingStrategyFactory instance = new PricingStrategyFactory();
	 private PricingStrategyFactory() {};
	 public static PricingStrategyFactory getInstance() 
	 {
			return instance;
	 }
	 
	 public IPricingStrategy getPricingStrategy(String BookType) 
	 {
		if(BookType.equals("A")) 
		{
			return new FlatRateStrategy(1);//教材类图书,每本1元折扣
		}
		else if(BookType.equals("B")) 
		{
			return new PercentageStrategy(7);//连环画类图书,每本7%折扣
		}
		else if(BookType.equals("C")) 
		{
			return new PercentageStrategy(3);//非教材类的计算机图书,每本3%折扣
		}
		else 
		{
			return new NoDiscountStrategy();//其它,没有折扣
		}
	}
}

interface IPricingStrategy
{
	public double getSubTotal(SaleLineItem sli);//得到单本图书优惠后的价格
}

class SaleLineItem 
{
	private int copies;
	private ProductSpecification prodSpec;
	private IPricingStrategy strategy;
	
	public SaleLineItem(int copies, ProductSpecification prodSpec, IPricingStrategy strategy)
	{
		this.copies = copies;
		this.prodSpec = prodSpec;
		this.strategy = strategy;
	}
	public double getSubTotal() 
	{
		return copies*(strategy.getSubTotal(this));
    } //得到此种图书,优惠后的价格
	public ProductSpecification getPro()
	{
		return prodSpec;
	}
}

class FlatRateStrategy implements IPricingStrategy
{
	private double discountPerBook;
	public FlatRateStrategy(double a){
		discountPerBook = a;
	}  //构造函数
	
	public double getSubTotal(SaleLineItem sli) {
		return sli.getPro().getPrice()-discountPerBook; //原先的价格-优惠的价格
	}
}

class PercentageStrategy implements IPricingStrategy
{
	private int discountPercentage;
	public PercentageStrategy(int a) 
	{
		discountPercentage = a;
	}
	
	public double getSubTotal(SaleLineItem sli) 
	{
		double discount = discountPercentage/100.0;
		return sli.getPro().getPrice()*(1-discount);
		//原先的价格*(1-折扣力度)
	}
}

class NoDiscountStrategy implements IPricingStrategy
{
	 public NoDiscountStrategy() {} //构造函数
	 public double getSubTotal(SaleLineItem sli) 
	 {
		 return sli.getPro().getPrice();//直接返回价格
	 }
}

class Sale
{
	private ArrayList<SaleLineItem> list = new ArrayList();
	public Sale() {}
	
	public void addItem(SaleLineItem it) 
	{		
	   list.add(it);
	}
	public double getTotal() 
	{
	    double total =0;
	    for(Iterator<SaleLineItem> iter = list.iterator();iter.hasNext();) 
	    {
	    	total = total + iter.next().getSubTotal();
	    }
	    	return total;
	} 
}

你可能感兴趣的:(北邮JAVA高级语言程序设计(选修课)设计模式大作业)