winston 发表于 2011-12-27 13:41:59

软件架构初体验

近两个月来,自己都在架构设计中痛苦挣扎着。很多人都会奇怪,做架构设计是多么另人心动的事情呀,怎么会痛苦呢?原因很简单,就是我不会!本人就职以来并没有系统的学习过架构设计,只是在工作中用到过一些如UML画类图等知识,而更多的,就是上头分配任务给我做,而让我从头做架构设计,从来没有过。我不知从何开始。
         对不知的事物,我都是从搜索引擎开始。我在网络上畅游,想找到对我有用的东西,可是我发现用架构这个关键词去搜索,找到很多的是软件架构这个词条,还有一些网址。我把词条通读后,发现对我还是有帮助的(因为我是零基础),但这好像远远不够。我想找这方面的教程,找到一些培训的课程的目录,里面好多都是我想学习的,但是并没有找到书籍。尝试过不同关键字后,找到了两本外文书,是叙述如何做框架的,专业术语太多,我只好先放弃了。功夫不负有心人,找到了两本中文教程。开始了我的边学边实践的旅程。整个过程是很痛苦的,因为身边并没有人给你指导,只能靠着一两本书,自己也不知道书中是否就是适合自己的,就这样的摸索着,在最后完成后才感受到一些喜悦。
      其实无论做什么事,都要清楚要干什么。这在我们做软件中就是要深入理解需求。这一点说起来容易,做起来很难。我的痛苦经历告诉我,表达不清的需求太多,不明确就意味着这个东西不好做。很多时候,客户是表达不清自己要什么的,那么需要我们去引导。这时有经验的大牛就会发挥很大的左右。还有很多功能点遗漏,不定什么时候客户想起来了,让你给加上。需求的不确定,对架构的要求就很高了。能够支持扩展的架构才是好架构。
         从需求中找出重点功能,围绕着它塑造你的概念架构。有位老师这样总结到:有这样两种常见的情况,业务流程不变而业务单元可变,方案就是利用设计模式构建软件框架;另一种是业务单元不变而流程变化,方案就是需要适应业务流程敏捷性处理的面向服务的架构。我遇到的情况属于第一种。
      我需要一种框架。这方面我得到了同事的大力支持。给出了非常好的适应变化的框架。举个耳熟能详的例子,《Java编程思想》中讲解内部时引入了一个Control框架,对,就是这种思想。
//: Event.java
// The common methods for any control event
package c07.controller;

abstract public class Event {
private long evtTime;
public Event(long eventTime) {
    evtTime = eventTime;
}
public boolean ready() {
    return System.currentTimeMillis() >= evtTime;
}
abstract public void action();
abstract public String description();
} ///:~/: Controller.java
// Along with Event, the generic
// framework for all control systems:
package c07.controller;

// This is just a way to hold Event objects.
class EventSet {
private Event[] events = new Event;
private int index = 0;
private int next = 0;
public void add(Event e) {
    if(index >= events.length)
      return; // (In real life, throw exception)
    events = e;
}
public Event getNext() {
    boolean looped = false;
    int start = next;
    do {
      next = (next + 1) % events.length;
      // See if it has looped to the beginning:
      if(start == next) looped = true;
      // If it loops past start, the list
      // is empty:
      if((next == (start + 1) % events.length)
         && looped)
      return null;
    } while(events == null);
    return events;
}
public void removeCurrent() {
    events = null;
}
}

public class Controller {
private EventSet es = new EventSet();
public void addEvent(Event c) { es.add(c); }
public void run() {
    Event e;
    while((e = es.getNext()) != null) {
      if(e.ready()) {
      e.action();
      System.out.println(e.description());
      es.removeCurrent();
      }
    }
}
} ///:~那么如何使用呢?一个greenhouse的例子:
//: GreenhouseControls.java
// This produces a specific application of the
// control system, all in a single class. Inner
// classes allow you to encapsulate different
// functionality for each type of event.
package c07.controller;

public class GreenhouseControls
    extends Controller {
private boolean light = false;
private boolean water = false;
private String thermostat = "Day";
private class LightOn extends Event {
    public LightOn(long eventTime) {
      super(eventTime);
    }
    public void action() {
      // Put hardware control code here to
      // physically turn on the light.
      light = true;
    }
    public String description() {
      return "Light is on";
    }
}
private class LightOff extends Event {
    public LightOff(long eventTime) {
      super(eventTime);
    }
    public void action() {
      // Put hardware control code here to
      // physically turn off the light.
      light = false;
    }
    public String description() {
      return "Light is off";
    }
}
private class WaterOn extends Event {
    public WaterOn(long eventTime) {
      super(eventTime);
    }
    public void action() {
      // Put hardware control code here
      water = true;
    }
    public String description() {
      return "Greenhouse water is on";
    }
}
private class WaterOff extends Event {
    public WaterOff(long eventTime) {
      super(eventTime);
    }
    public void action() {
      // Put hardware control code here
      water = false;
    }
    public String description() {
      return "Greenhouse water is off";
    }
}
private class ThermostatNight extends Event {
    public ThermostatNight(long eventTime) {
      super(eventTime);
    }
    public void action() {
      // Put hardware control code here
      thermostat = "Night";
    }
    public String description() {
      return "Thermostat on night setting";
    }
}
private class ThermostatDay extends Event {
    public ThermostatDay(long eventTime) {
      super(eventTime);
    }
    public void action() {
      // Put hardware control code here
      thermostat = "Day";
    }
    public String description() {
      return "Thermostat on day setting";
    }
}
// An example of an action() that inserts a
// new one of itself into the event list:
private int rings;
private class Bell extends Event {
    public Bell(long eventTime) {
      super(eventTime);
    }
    public void action() {
      // Ring bell every 2 seconds, rings times:
      System.out.println("Bing!");
      if(--rings > 0)
      addEvent(new Bell(
          System.currentTimeMillis() + 2000));
    }
    public String description() {
      return "Ring bell";
    }
}
private class Restart extends Event {
    public Restart(long eventTime) {
      super(eventTime);
    }
    public void action() {
      long tm = System.currentTimeMillis();
      // Instead of hard-wiring, you could parse
      // configuration information from a text
      // file here:
      rings = 5;
      addEvent(new ThermostatNight(tm));
      addEvent(new LightOn(tm + 1000));
      addEvent(new LightOff(tm + 2000));
      addEvent(new WaterOn(tm + 3000));
      addEvent(new WaterOff(tm + 8000));
      addEvent(new Bell(tm + 9000));
      addEvent(new ThermostatDay(tm + 10000));
      // Can even add a Restart object!
      addEvent(new Restart(tm + 20000));
    }
    public String description() {
      return "Restarting system";
    }
}
public static void main(String[] args) {
    GreenhouseControls gc =
      new GreenhouseControls();
    long tm = System.currentTimeMillis();
    gc.addEvent(gc.new Restart(tm));
    gc.run();
}
} ///:~
有了这种框架的思想,下面就容易做到“把稳定和变化分离开”,做到封装变化。

细化架构的时候,需要确定各模块的接口和数据结构。一个好的数据结构会让你的架构增光不少。一个原则,就是要把数据结构设计好,让其适应变化。
这个时候就可以开始基类的定义了,画类图、时序图等等。文档也是必不可少。
这方面我还没有好好做就开始编码了,而且框架也在适当的修改着。
这只是一个开始,以后还能有机会做设计,就不会想这次这样痛苦和难堪了。
作者:lincyang 发表于2011-12-26 21:04:22 原文链接
页: [1]
查看完整版本: 软件架构初体验