开发者头条

餐厅老板要累疯了No.2

2017-07-02  本文已影响7人  一名叫大蕉的程序员

我是小蕉。

从前有座山,山里有座庙,庙里有个老和尚,阿不,有个餐厅的老板,在每天午餐之前,都要自己亲力亲为为各个小伙伴分配任务,大喊一声开饭啦,大家就屁颠屁颠跑过来领任务。炒菜嘛,就交给A来做,他的厨艺好。搬桌子嘛,交给B来做,他身强力壮。煮饭嘛,交给C来做,他比较细心。陪客人唠嗑嘛,就交给小蕉,毕竟他嘴皮子可厉害了。每天都这样,虽然很累,但老板倒也乐此不疲。直到有一天。

餐厅发展越来越好,员工越来越多,老板的员工达到了19876名,老板明显已经力不从心了,经常记错员工的名字,也经常记错要给员工安排的任务,又一次竟然把我当成隔壁老王,让我去扫厕所T_T。这也太委屈了,该怎么帮帮老板,顺便帮帮我自己呢?

在老板累死之前,我决定做一点事情,来解除这个死循环。

我们换一个思路,每个员工在入职的时候都会得到一份”工作要点“,然后老板快开饭的时候大喊一声,开饭啦。各个员工就观察老板的脸色,就各自行动去啦。A呢就自己去炒菜,搬桌子的事情就交给B啦,C自从没被派去扫地饭也煮得越来越好吃,一切都好起来了。

按照这样安排呢,这样后面就算新进一个员工,也只是多一发一份工作要点的事。

辟如一个员工太老了炒不了菜,给他换一份说明或者直接办理退休不处理事务就,在老板喊开饭的时候就直接忽略就好。就在机智的小蕉的建议下,老板进行了组织重整,终于闲下来了,又回到了整天唠嗑收钱的好日子了,我呢,也再也没有被派去扫厕所。

这!!!天哪!!!这跟今天要大家分享的,在实际工作中遇到的一个问题不谋而合啊!!!就是if else!!!看过一个多分支任务重跑类,就是由一个CODE来决定如何重跑。我的屏幕有24寸那么长,一屏幕看下来,满屏幕都是if else!!!What the。

if(some){}

else if(some else){

if(some){}

else{}

}

else if(some others){}

else if(some etc.){}...

看着这些代码这太难受了,后面也不好维护啊,这后面加一个功能岂不是要废?这么一大坨万一我还不敢轻易改,怕怕,怕怕。本着“我不管我就要改的”的善心,我决定重构一下这个代码。说走咱就走啊。天上的星星参北斗啊...

下面是纯技术干货,非技术宅的看官老爷可以直接左上角退出。

我们项目使用的是SpringMVC嘛,所以就大胆地使用Spring容器了。首先要有一个定时JOB吧,不然怎么来设计重跑,经验上来说,每五分钟跑一次,跑三次不成功,要么就是目标服务有问题,要么就是本地抛异常挂掉了。那就脑袋一拍,咱就使用观察者模式,让各个执使用Quartz来驱动这个定时任务好了。 定义一个bean然后类是下面这个,还有targetMethod属性要定义好就行了。

class="org.springframework.scheduling.quartz.MethodInvokingJobDetailFactoryBean">

定义一个调度中心,也就是上面那玩意,用来管理整批的重跑任务。

@Service(ObserverCenter.SERVICE_ID)

class ObserverCenter{

public static final String SERVICE_ID="ObserverCenter";

//hold住所有的调度任务处理器,在下面会定义的

List registedObservers = new ArrayList();

//提供一个给处理器注册的接口

public void register(Observer observer){

this.registedObservers.add(observer);

}

//提供一个给处理器注销的接口

public void unRegister(Observer observer){

this.registedObservers.remove(observer);

}

//Quartz执行的方法

public void execute(){

//获得需要重跑的任务列表

List somethingNeedToRun = new ArrayList();

//将任务广播到所有的任务观察者中,由观察者决定是否处理以及如何处理

for(SomeRecords somethingNeedToRun in somethingNeedToRun){

for(Observer observer : registedObservers){

observer.handle(somethingNeedToRun);

}

}

}

}

好了,驱动类写完啦~谈谈观察类的子类把。首先会定义一个抽象类,作为所有调度任务的父类。每个观察者类都会注册到调度中心,所以预先实现好调度方法。@PostConstruct注解用于在实例构造完执行,这里用于把自己注册到调度中心。@PreDestory注解用于在实例销毁之前,这里用于把自己从调度中心注销。

public abstract class Observer(){

@Resource(name=ObserverCenter.SERVICE_ID)

private ObserverCenter observerCenter;

@PostConstruct

private registerToCenter(){

observerCenter.register(this);

}

@PreDestory

private unRegisterFromCenter(){

observerCenter.register(this);

}

void abstract handle(SomeRecords);

}

定义一个抽记录类。

public class SomeRecords{

}

每个继承了Observer的子类,在使用Spring的单实例模式,被容器构造完成后,都会自动注册到调度中心,在接受到来自调度中心的任务后,各个子类可以决定自己需不需要处理,以及怎么处理。接下来是一个驱动类的DEMO,

public class extends Observer(){

@Override

public void handle(SomeRecords){

Logger.log("I don't give a shit to the record!")

}

}

在这个设计模式下,不会有非常长的if else,可维护性大大提高。后续在增加一个调度子类,以及删除一个调度子类,都非常方便,不会影响任何其他的处理器。

好啦今天的分享就到这里,大家有什么建议可以在后台吐槽,反正我也不会回的,毕竟我懒。

上一篇下一篇

猜你喜欢

热点阅读