灰太狼 2017-05-18 12:05:08 2261次浏览 2条回复 5 5 0

小菜技术分享第二篇。

场景:经理A的咖啡店今天开业了,经理A找到小菜,让他帮忙设计一个销售程序(私下交易,经理A照顾小菜,给小菜个私活) 仔细分析,咖啡店肯定会卖多种咖啡,不同咖啡不同口味,不同顾客选用不同搭配,比如有的顾客要加糖,有的不加,有的加奶,有的不加。

这样的话怎么搞呢? 先用我们低级的思维--过程开发写一下试试

class Coffee{
   //销售咖啡
   public function saleCoffee(){
        $coffeeType = '接收用户指令需要什么咖啡';
        $suggar = '接收用户加糖''接收用户加糖''';
        $milk = '接收用户加奶''接收用户加奶''';
        $coffee = '';
	$_suggar = $_milk = null;
       	switch($coffeeType){
       		case '黑咖啡':
       			$coffee = $this->createCoffee_Black();
       			break;
       		case '摩卡':
       			$coffee = $this->createCoffee_Mocha();
       			break;
       		case '拿铁':
       			$coffee = $this->createCoffee_Latte();
       			break;
       		case '美式':
       			$coffee = $this->createCoffee_Americano();
       			break;
	}
        //是否需要加糖
	if($suggar){
		$_suggar = $this->addSuggar($coffee);
	}
	//是否需要加奶
	if($milk){
		$_milk = $this->addSuggar($coffee);
	}

	//将咖啡,糖返回给用户
	return array][$coffee,$_suggar,$_milk];//如果没有奶,没有糖,返回空;
   }
   //制作一杯黑咖啡
   private function createCoffee_Black(){
   		//工序不同,配料不同,杯子不同
   		return $coffee;//制作完成,返回一杯咖啡
   }
   //制作一杯摩卡
   private function createCoffee_Mocha(){
   		/工序不同,配料不同,杯子不同
   		return $coffee;//制作完成,返回一杯咖啡
   }
   //制作一杯拿铁
   private function createCoffee_Latte(){
   		//工序不同,配料不同,杯子不同
   		return $coffee;//制作完成,返回一杯咖啡
   }
   //制作一杯美式
   private function createCoffee_Americano(){
   		/工序不同,配料不同,杯子不同
   		return $coffee;//制作完成,返回一杯咖啡
   }

   //加糖
   private function addSuggar(){
   		//收糖钱1元(一般情况是不要钱的,为了例子需要,这里加糖要钱)
   		return 糖;
   }
   //加奶
   private function addMilk(){
	    //收奶钱1元(一般情况是不要钱的,为了例子需要,这里加糖要钱)
	    return 奶;
   }
}

程序手打,没有测试,会有错误。 仔细看就知道了,如果以后经理A咖啡店增加了其他品种的咖啡或其他品种的配料 要修改的地方会很多。 而且或多了很多if else 的判断。这种if else 分支判断多了,整个程序就会越来越乱。

对于开发,if else 判断不是说用的越多越不好。而是,对于这种组合模式的程序,使用if else判断完全是行不通的,以为你不确定组合的基数是多少,后续扩展。 而真正使用if else 的是,两条路选择时,对于与后续无扩展变化。例如if(是会员){有人会说了,后续会员会有多个等级也是不确定的,这个具体等级就是细分了,但是,不管什么等级,他们都是会员所以可以用if else 后续再处理多个等级的会员,V1,V2,V3...这是不建议用if else}else{} . PS(这里啰嗦了一下) 完全是个人想法,有不同想法的欢迎留言批评。

继续 改用面向对象的来开发

做面向对象,第一步就是分析,先不急着写代码。分析就是抽象思维来思考。什么是抽象思维呢就是看待事物从不同角度出发: 例如, 平常人看两个人在散步,可以抽象为人类,两个人类在散步(他的眼里是两个人在走路) 生物学家看两个人在散步,可以抽象为动物,两个人在散步(他的眼里是两个动物在走路)(往高粒度分析人也是动物) 细胞学家看两个人在散步,可以抽象为细胞,两个人在散步(他的眼里是两堆细胞在移动) (往更高的粒度分析了)

回到正题, 咖啡店,咖啡怎么分析

1咖啡属于咖啡? 2咖啡属于饮品? 3咖啡属于液体?

你觉得上面三个抽象,哪个合适? 我觉得是2。虽然1也是可以的,但是对于后续扩展不广,如果以后经理A的咖啡店卖奶茶了呢?抽象类如果是1咖啡的话,奶茶不属于咖啡啊! 但是如果抽象为饮品,以后咖啡店升级卖奶茶了也可以继承饮品类,以后买果汁了也没问题。。。 如果选3抽象为液体,这个维度有点高了,就目前的需求是用不到(如果是安检系统或许会用到)

abstract class Drink{
    public $name;//饮品名字
    //饮品
    abstract public function sale();
}

abstract class Coffee extends Drink{
    public function beizi(){
        //所有咖啡统一用陶瓷杯子
    }
    abstract public function sale();
}

//黑咖啡
class Coffee_Black extends Coffee{
     public function __construct(){
         $this->name = '黑咖啡';
     }
     public function sale(){
        //咖啡销售价格
        return 35;
     }
}
//摩卡
class Coffee_Mocha extends Coffee{
     public function __construct(){
         $this->name = '摩卡';
     }
     public function sale(){
         return 30;
     }
}
//拿铁
class Coffee_Latte extends Coffee{
     public function __construct(){
         $this->name = '拿铁';
     }
     public function sale(){
         return 25;
     }
}
//美式
class Coffee_Americano extends Coffee{
     public function __construct(){
         $this->name = '美式';
     }
     public function sale(){
         return 28;
     }
}

//装饰器
class Decorator extends Drink{
    private $_drink;
    public function __construct(Drink $drink){
         $this->_drink = $drink;
    }
}

//加糖
class Suggar extends Decorator{
      public function sale(){
         //加糖,在原金额基础上+1元
         return $this->_drink->sale()+1;
      }
}
//加奶
class Milk extends Decorator{
     public function sale(){
          //加奶,在原金额基础上+1元
          return $this->_drink->sale()+1;
     }
}
//后续扩展,如果加酒就单独写一个类,加什么都单独一个类,与其他代码不发生冲突。
开放封闭原则

收银台调用:
要一杯美式咖啡,加糖,加奶
public function client(){
    //美式咖啡
    $Americano = new Coffee_Americano();
    $suggar  = new Suggar($Americano);
    $milk = new Milk($suggar );
    echo $milk->name;
    echo $milk->sale();
}

累了,不写了,大概就这意思。 代码没验证。有错正常。 为自己记录:2017年5月18日 今天爱车被电瓶车装了,妈的,太气人了。没赔钱就走了

觉得很赞
您需要登录后才可以回复。登录 | 立即注册