设计商场收银软件 根据客户需求购买的单价和数量,计算总额

商场需求:打折和满减


简单工厂弄湿每次维护或扩展收费都要改动这个工厂,以至于代码需要重新编译部署

引入策略模式:定义算法家族,分别封装起来,让他们之间可以互相替换,此模式让算法的变化,不会影响到使用算法的客户

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
namespace 策略模式
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }
        abstract class CashSuper
        {
            public abstract double acceptCash(double money);
        }
        class CashNormal : CashSuper
        {
            public override double acceptCash(double money) { return money; }
        }
        class CashRebate : CashSuper
        {
            private double moneyRebate = 1d;
            public CashRebate(string moneyRebate)
            {
                this.moneyRebate = double.Parse(moneyRebate);
            }
            public override double acceptCash(double money)
            {
                return money * moneyRebate;
            }
        }
        class CashReturn : CashSuper
        {
            private double moneyCondition = 0.0d;
            private double moneyReturn = 0.0d;
            public CashReturn(string moneyCondition, string moneyReturn)
            {
                this.moneyCondition = double.Parse(moneyCondition);
                this.moneyReturn = double.Parse(moneyReturn);
            }
            public override double acceptCash(double money)
            {
                double result = money;
                if (money >= moneyCondition)
                    result = money - Math.Floor(money / moneyCondition) * moneyReturn;
                return result;
            }
        }
        class CashContext
        {
            private CashSuper cs;
            public CashContext(CashSuper csuper)
            {
                this.cs = csuper;
            }
            public double GetResult(double money)
            {
                return cs.acceptCash(money);
            }
        }

        double total = 0.0d;
        private void button1_Click(object sender, EventArgs e)
        {
            CashContext cc = null;
            switch(listBox1.SelectedItem.ToString())
            {
                case "正常收费":
                    cc=new CashContext(new CashNormal());
                    break;
                case "打8折":
                    cc=new CashContext(new CashRebate("0.8"));
                    break;
                case "满300反100":
                    cc=new CashContext(new CashReturn("300","100"));
                    break;
            }
            double totalPrices=0d;
            totalPrices=cc.GetResult(Convert.ToDouble(textBox1.Text)*Convert.ToDouble(textBox2.Text));
            total=total+totalPrices;
            label5.Text=total.ToString();
        }
    }
}
如何将判断不放在客户端

策略+简单工厂

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
namespace 策略模式
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }
        abstract class CashSuper
        {
            public abstract double acceptCash(double money);
        }
        class CashNormal : CashSuper
        {
            public override double acceptCash(double money) { return money; }
        }
        class CashRebate : CashSuper
        {
            private double moneyRebate = 1d;
            public CashRebate(string moneyRebate)
            {
                this.moneyRebate = double.Parse(moneyRebate);
            }
            public override double acceptCash(double money)
            {
                return money * moneyRebate;
            }
        }
        class CashReturn : CashSuper
        {
            private double moneyCondition = 0.0d;
            private double moneyReturn = 0.0d;
            public CashReturn(string moneyCondition, string moneyReturn)
            {
                this.moneyCondition = double.Parse(moneyCondition);
                this.moneyReturn = double.Parse(moneyReturn);
            }
            public override double acceptCash(double money)
            {
                double result = money;
                if (money >= moneyCondition)
                    result = money - Math.Floor(money / moneyCondition) * moneyReturn;
                return result;
            }
        }
        class CashContext
        {
            CashSuper cs=null;
            public CashContext(string type)
            {
                switch (type)
                {
                    case "正常收费":
                        CashNormal cs0 = new CashNormal();
                        cs = cs0;
                        break;
                    case "打8折":
                        CashRebate cs1 = new CashRebate("0.8");
                        cs = cs1;
                        break;
                    case "满300反100":
                        CashReturn cs2 = new CashReturn("300", "100");
                        cs = cs2;
                        break;
                }
            }
            public double GetResult(double money)
            {
                return cs.acceptCash(money);
            }
        }

        double total = 0.0d;
        private void button1_Click(object sender, EventArgs e)
        {
            CashContext csuper = new CashContext(listBox1.SelectedItem.ToString());
            double totalPrices=0d;
            totalPrices=csuper.GetResult(Convert.ToDouble(textBox1.Text)*Convert.ToDouble(textBox2.Text));
            total=total+totalPrices;
            label5.Text=total.ToString();
        }
    }
}

利用反射机制
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.Reflection;

namespace 商场管理软件
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        DataSet ds;//用于存放配置文件信息
        double total = 0.0d;//用于总计

        private void Form1_Load(object sender, EventArgs e)
        {
            //读配置文件
            ds = new DataSet();
            ds.ReadXml(Application.StartupPath + "\\CashAcceptType.xml");
            //将读取到的记录绑定到下拉列表框中
            foreach (DataRowView dr in ds.Tables[0].DefaultView)
            {
                cbxType.Items.Add(dr["name"].ToString());
            }
            cbxType.SelectedIndex = 0;
        }

        private void btnOk_Click(object sender, EventArgs e)
        {
            CashContext cc = new CashContext();
            //根据用户的选项,查询用户选择项的相关行
            DataRow dr = ((DataRow[])ds.Tables[0].Select("name='" + cbxType.SelectedItem.ToString()+"'"))[0];
            //声明一个参数的对象数组
            object[] args =null;
            //若有参数,则将其分割成字符串数组,用于实例化时所用的参数
            if (dr["para"].ToString() != "")
                args = dr["para"].ToString().Split(',');
            //通过反射实例化出相应的算法对象
            cc.setBehavior((CashSuper)Assembly.Load("商场管理软件").CreateInstance("商场管理软件." + dr["class"].ToString(), false, BindingFlags.Default, null, args, null, null));
            
            double totalPrices = 0d;
            totalPrices = cc.GetResult(Convert.ToDouble(txtPrice.Text) * Convert.ToDouble(txtNum.Text));
            total = total + totalPrices;
            lbxList.Items.Add("单价:" + txtPrice.Text + " 数量:" + txtNum.Text + " "+cbxType.SelectedItem+ " 合计:" + totalPrices.ToString());
            lblResult.Text = total.ToString();
        }

        private void btnClear_Click(object sender, EventArgs e)
        {
            total = 0d;
            txtPrice.Text = "0.00";
            txtNum.Text = "1";
            lbxList.Items.Clear();
            lblResult.Text = "0.00";
        }

        
    }
}

上面是书上的例子,昨天被对象问住了,发现自己学的不扎实啊T^T 对象举了cf acm比赛输出榜单的例子让我写

这个是单例模式的写法

class Program
    {
        abstract class contestSuper
        {
            public abstract string print(double number);
        }
        class cf: contestSuper
        {
            public override string print(double number)
            {
                return "cfboard"+"  人数:"+number.ToString();
            }
        }
        class acm: contestSuper
        {
            public override string print(double number)
            {
                return "acmbroad" + "  人数:" + number.ToString();
            }
        }
        class showBoard
        {
            public static contestSuper createBoard(string type)
            {
                contestSuper cs=null;
                switch(type)
                {
                    case "cf":
                        cs = new cf();
                        break;
                    case "acm":
                        cs = new acm();
                        break;
                }
                return cs;
            }
        }
        static void Main(string[] args)
        {
            contestSuper cs = showBoard.createBoard("cf");
            string text = "";
            text = cs.print(30);
            Console.WriteLine(text);
            cs = showBoard.createBoard("acm");
            text = cs.print(30);
            Console.WriteLine(text);
            Console.Read();
        }
    }

策略模式

abstract class contestSuper
        {
            public abstract string print(double number);
        }
        class cf : contestSuper
        {
            public override string print(double number)
            {
                return "cfboard" + "  人数:" + number.ToString();
            }
        }
        class acm : contestSuper
        {
            public override string print(double number)
            {
                return "acmbroad" + "  人数:" + number.ToString();
            }
        }
        class printContext
        {
            private contestSuper cs;
            public printContext(contestSuper cs)
            {
                this.cs = cs;
            }
            public string createBoard(double number)
            {
                return cs.print(number);
            }
        }

        static void Main(string[] args)
        {
            printContext pc = null;
            string text = "acm";
            switch (text)
            {
                case "acm":
                    pc = new printContext(new acm());
                    break;
                case "cf":
                    pc = new printContext(new cf());
                    break;
            }
            text = pc.createBoard(30);
            Console.WriteLine(text);
            Console.Read();
        }


简单工厂+策略模式

 class Program
    {
        abstract class contestSuper
        {
            public abstract string print(double number);
        }
        class cf : contestSuper
        {
            public override string print(double number)
            {
                return "cfboard" + "  人数:" + number.ToString();
            }
        }
        class acm : contestSuper
        {
            public override string print(double number)
            {
                return "acmbroad" + "  人数:" + number.ToString();
            }
        }
        class showBoard
        {
            contestSuper cs = null;

            public showBoard(string type)
            {
                switch (type)
                {
                    case "acm":
                        acm sb0 = new acm();
                        cs = sb0;
                        break;
                    case "cf":
                        cf sb1 = new cf();
                        cs = sb1;
                        break;
                }
                
            }
            public string createBoard(double number)
            {
                return cs.print(number);
            }
        }

        static void Main(string[] args)
        {
            showBoard sb = new showBoard("acm");
            Console.WriteLine(sb.createBoard(30));
            Console.Read();
        }
    }