质量属性 可修改
而根据文中所讲述的,一个系统的可用性主要是体现在这个系统的系统服务不中断运行时间占实际运行时间的比例,系统的伸缩性则是指在不改变系统软硬件设计,仅仅通过新增服务器的情况下,就能提升系统的处理能力,而系统的可扩展性是指该系统适应变化的能力。
局部化如下
我自己对可修改性的理解:可修改性的理解,引起可修改性的因素,根据软件设计原则分析对可修改性的相关战术进行个人分析,分为了以下几个方面:
可修改性描述了程序能够被正确修改的难易程度。一个可修改的程序应当是可理解的、通用的、简单的、灵活的。通用性是指程序适用于各种功能变化而无需修改。灵活性是指能够容易地对程序进行修改。
以下因素也会对系统的可维护性产生重要影响:
(1)开发人员是否受过严格的规范化培训。
(2)是否采用标准化的文档资料结构和文档形成机制。
(3)是否采用可维护的程序设计语言。
(4)是否有健全程序的文档。
(5)是否保存规范化的测试资料等。
如javabean+severt+html
实现各个模块的可修改性数据文件修改不影响其他代码修改,前端与后台相隔离
1. 设计网站可扩展架构的核心思想是模块化,并在此基础上降低模块间的耦合性,提高模块复用性。
2. 模块化的重要手段:分层和分割,分层、分割为若干个低耦合的独立组件模块(模块可分布式部署,从物理上分离模块间耦合),各模块以消息传递及依赖调用方式聚合成完整系统。
可修改性战术
控制可修改性的战术,其目标是控制实现、测试和部署变更的时间和成本。
1、局部化变更:维持语义的一致性;预期期望的变更;泛化该模块;限制可能的选择;抽象通用服务;
2、防止连锁反应:信息隐藏;维持现有的接口;限制通信路径;仲裁者的使用;
3、推迟绑定时间:运行时注册;配置文件;多态;组件更换;遵守已定义的协议;
局部性:
try-catch 情景 function loadPackage(packageName){ try{ let packageInfo = getPackageInfo(packageName); let configPath = packageInfo.path + '/config.json'; let package = JSON.parse(fs.readFileSync(configPath)); return package; }catch(err){ return null; } }
典型代码
lock 情景 typedef std::map<K*,V*> Dict; Dict dict; Lock* lock = new Lock(); int Add(K* key, V* value){ lock->lock(); Dict::iterator it = dict.find(key); if (it == Dict.end()){ key->AddRef(); value->AddRef(); dict.insert(std::make_pair(key, value)); } lock->unlock(); return RESULT.SUCCESS; } int Remove(K* key){ lock->lock(); K* oldKey = NULL; V* oldValue = NULL; Dict::iterator it = dict.find(key); if (it != dict.end()){ oldKey = it->first; oldValue = it->second; dict.erase(it); } if (oldKey){ oldKey->Release(); } if (oldValue){ oldValue->Release(); } lock->unlock(); return RESULT.SUCCESS; } V* Find(K * key){ lock->lock(); K* oldKey = NULL; V* oldValue = NULL; dict::iterator it = dict.find(key); if (it != dict.end()) { oldKey = it->first; oldValue = it->second; } oldValue->AddRef(); lock->unlock(); return oldValue; }
2.读取数据,建立bean文件实现模板化的可修改性 隐藏属性
package reci.bean; public class wordBean { private int id; private String words; private String content; private int counts; public wordBean() { super(); // TODO Auto-generated constructor stub } public wordBean(int id, String words, String content, int counts) { super(); this.id = id; this.words = words; this.content = content; this.counts = counts; } public int getCounts() { return counts; } public void setCounts(int counts) { this.counts = counts; } public int getId() { return id; } public void setId(int id) { this.id = id; } public String getWords() { return words; } public void setWords(String words) { this.words = words; } public String getContent() { return content; } public void setContent(String content) { this.content = content; }
三 xml文件 利用它可不用修改代码就能轻松的修改参数(推迟绑定时间)
<?xml version="1.0" encoding="UTF-8"?><students> <student> <name>Tom</name> <age>11</age> </student> <student> <name>Bob</name> <age>22</age> </student> <student> <name>Marry</name> <age>23</age> </student></students
DOM 解析
import java.io.FileOutputStream; import javax.xml.parsers.DocumentBuilder;import javax.xml.parsers.DocumentBuilderFactory;import javax.xml.transform.Transformer;import javax.xml.transform.TransformerFactory;import javax.xml.transform.dom.DOMSource;import javax.xml.transform.stream.StreamResult; import org.w3c.dom.Document;import org.w3c.dom.Element;import org.w3c.dom.Node;import org.w3c.dom.NodeList; public class DomParser{ /** * 解析器读入整个文档,然后构建一个驻留内存的树结构, * 该方法返回 Document 对象,然后我们可以通过 这个对象来操作文档 */ public Document getDocument(String fileName) throws Exception{ //1.创建解析工厂 DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance(); //2.得到解析器 DocumentBuilder dBuilder = dbFactory.newDocumentBuilder(); //3.得到文档对象 Document document = dBuilder.parse(fileName); return document; } //读取xml文档中的数据 public void read(String fileName) throws Exception{ //获取 Document 对象 Document document = new DomParser().getDocument(fileName); //获取<name></name>的节点 NodeList nameNode = document.getElementsByTagName("name"); //获取<name sex="xxx"></name>节点的sex属性 Element element = (Element) document.getElementsByTagName("name").item(0); System.out.println(element.getAttribute("sex"));//xxx for(int i = 0 ; i < nameNode.getLength() ;i++){ System.out.println(nameNode.item(i).getTextContent()); } /**结果为 * Tom * Bob * Marry */ //获取文档的根元素对象 Element rootElementName = document.getDocumentElement(); System.out.println(rootElementName.getNodeName()); //students //得到根节点 Node root = document.getElementsByTagName(rootElementName.getNodeName()).item(0); list(root); } //打印所有标签 private void list(Node root) { if(root instanceof Element){ System.out.println(root.getNodeName()); } NodeList list = root.getChildNodes(); for(int i = 0 ; i < list.getLength() ; i++){ Node child = list.item(i); list(child); } } //向 xml 文件中增加节点和属性 public void add(String fileName) throws Exception{ //获取 Document 对象 Document document = new DomParser().getDocument(fileName); //创建节点 Element sex = document.createElement("sex"); sex.setTextContent("男"); //把创建的节点添加到第一个<student></student>标签上 Element student = (Element) document.getElementsByTagName("student").item(0); student.appendChild(sex); //在<name></name>中增加属性 <name address="xxx"></name> Element name = (Element) document.getElementsByTagName("name").item(0); name.setAttribute("address", "xxx"); //把更新后的内存写入xml文档中 TransformerFactory tfFactory = TransformerFactory.newInstance(); Transformer tFormer = tfFactory.newTransformer(); tFormer.transform(new DOMSource(document), new StreamResult(new FileOutputStream("src/student.xml"))); } //向 xml 文件中删除节点和属性 public void delete(String fileName) throws Exception{ //获取 Document 对象 Document document = new DomParser().getDocument(fileName); //得到要删除的第一个<name></name>节点 Element name = (Element) document.getElementsByTagName("name").item(0); //得到要删除的第一个<name></name>节点的父节点 //Element student = (Element) document.getElementsByTagName("student").item(0); //student.removeChild(name); //上面两步可以简写为 name.getParentNode().removeChild(name); //在<name></name>中删除属性 <name address="xxx"></name> name.removeAttribute("address"); //把更新后的内存写入xml文档中 TransformerFactory tfFactory = TransformerFactory.newInstance(); Transformer tFormer = tfFactory.newTransformer(); tFormer.transform(new DOMSource(document), new StreamResult(new FileOutputStream("src/student.xml"))); } //向 xml 文件中更新节点和属性 public void update(String fileName) throws Exception{ //获取 Document 对象 Document document = new DomParser().getDocument(fileName); //得到要删除的第一个<name></name>节点 Element name = (Element) document.getElementsByTagName("name").item(0); //在<name></name>中更新属性 <name address="xxx"></name>为<name address="yyy"></name> name.setAttribute("address", "yyy"); //更新name节点的文字为VAE,即<name>vae</name> name.setTextContent("vae"); //把更新后的内存写入xml文档中 TransformerFactory tfFactory = TransformerFactory.newInstance(); Transformer tFormer = tfFactory.newTransformer(); tFormer.transform(new DOMSource(document), new StreamResult(new FileOutputStream("src/student.xml"))); }}
四 利用设计模式
比如桥接模式
DisplayImpl类:虽然是实现层次,但却是抽象的。
1 package zyr.dp.bridge; 2 3 public abstract class DisplayImpl { 4 public abstract void rawOpen(); 5 public abstract void rawPrint(); 6 public abstract void rawClose(); 7 }
StringDisplayImpl类:
1 package zyr.dp.bridge; 2 3 public class StringDisplayImpl extends DisplayImpl { 4 5 String name; 6 public StringDisplayImpl(String name){ 7 this.name=name; 8 } 9 10 public void rawOpen() { 11 printline(); 12 } 13 14 public void rawPrint() { 15 System.out.println("|||||"+name+"|||||"); 16 } 17 18 public void rawClose() { 19 printline(); 20 } 21 private void printline(){ 22 System.out.println("================"); 23 } 24 25 }
Display 类:
1 package zyr.dp.bridge; 2 3 public class Display { 4 private DisplayImpl displayImpl ; 5 public Display(DisplayImpl displayImpl){ 6 this.displayImpl=displayImpl; 7 } 8 public void open(){ 9 displayImpl.rawOpen(); 10 } 11 public void print(){ 12 displayImpl.rawPrint(); 13 } 14 public void close(){ 15 displayImpl.rawClose(); 16 } 17 public final void display(){ 18 open(); 19 print(); 20 close(); 21 } 22 23 }
CountDisplay类:
1 package zyr.dp.bridge; 2 3 public class CountDisplay extends Display { 4 5 public CountDisplay(DisplayImpl displayImpl) { 6 super(displayImpl); 7 } 8 public final void mutilDisplay(){ 9 open(); 10 for(int i=0;i<5;i++){ 11 print(); 12 } 13 close(); 14 } 15 16 }
Main类:
package zyr.dp.bridge; public class Main { public static void main(String[] args) { Display display = new Display(new StringDisplayImpl("朱彦荣")); display.display(); CountDisplay cd = new CountDisplay(new StringDisplayImpl("李山秀")); cd.display(); cd.mutilDisplay(); }
}