首页 > 程序开发 > 软件开发 > Java >

Java序列化,反射,注解(二)

2016-09-12

Demo1:多层数据访问层切换事例,在多种数据库之间切换时而不影响其他代码的改变,根据面向对象的思想,使用MVC的设计模式

Demo1:多层数据访问层切换事例,在多种数据库之间切换时而不影响其他代码的改变,根据面向对象的思想,使用MVC的设计模式,一点一点的进行优化。

文件属于那个包中可自行比对,不在多说

第一版本:

结构目录:这里写图片描述

Depart.java://<喎"http://www.2cto.com/kf/ware/vc/" target="_blank" class="keylink">vcD4NCjxwcmUgY2xhc3M9"brush:java;"> package com.mq.class1.reflectdemo.entity; public class Depart { private int deptNo; private String name; public int getDeptNo() { return deptNo; } public void setDeptNo(int deptNo) { this.deptNo = deptNo; } public String getName() { return name; } public void setName(String name) { this.name = name; } public Depart() { super(); // TODO Auto-generated constructor stub } public Depart(int deptNo, String name) { super(); this.deptNo = deptNo; this.name = name; } @Override public String toString() { return "Depart [deptNo=" + deptNo + ", name=" + name + "]"; } }

IDepart.java:

package com.mq.class1.reflectdemo.dao;

import java.util.List;

import com.mq.class1.reflectdemo.entity.Depart;

public interface IDepart {

    /**
     * 通过部门ID查找部门
     * 
     * @param id
     * @return
     */
    public Depart getDepartById(int id);

    /**
     * 查找所有的部门
     * 
     * @return
     */
    public List getAllDepart();
}

DepartService.java:

package com.mq.class1.reflectdemo.mysqldaoImpl;

import java.util.List;

import com.mq.class1.reflectdemo.dao.IDepart;
import com.mq.class1.reflectdemo.entity.Depart;

public class DepartService implements IDepart{

    @Override
    public Depart getDepartById(int id) {
        System.out.println("mysql------------->根据编号"+id+",可以查找出相应的部门");
        return null;
    }

    @Override
    public List getAllDepart() {
        // TODO Auto-generated method stub
        System.out.println("mysql------------->查找出所有的部门");
        return null;
    }


}

DepartManager.java //重点

package com.mq.class1.reflectdemo.biz;

import java.util.List;

import com.mq.class1.reflectdemo.dao.IDepart;
import com.mq.class1.reflectdemo.entity.Depart;
import com.mq.class1.reflectdemo.mysqldaoImpl.DepartService;

public class DepartManager {

    private IDepart dao = null;

    /**
     * 在构造函数中创建dao层对象IDepart
     */
    public DepartManager() {
        // TODO Auto-generated constructor stub
        dao = new DepartService();
    }

    public Depart getDepartById(int id) {
        dao.getDepartById(id);
        return null;
    }

    public List getAllDepart() {
        // TODO Auto-generated method stub
        dao.getAllDepart();
        return null;
    }
}

第二版本

如果要更改连接的数据库为sql server,要符合面向对象的open-close的原则,则最好不要动原来的代码,应该增加一个包,存放使用sql server数据库的代码

结构目录:
这里写图片描述

DepartService.java

package com.mq.class1.reflectdemo.sqlserverdaoImpl;

import java.util.List;

import com.mq.class1.reflectdemo.dao.IDepart;
import com.mq.class1.reflectdemo.entity.Depart;

public class DepartService implements IDepart{

    @Override
    public Depart getDepartById(int id) {
        System.out.println("sql server------------->根据编号"+id+",可以查找出相应的部门");
        return null;
    }

    @Override
    public List getAllDepart() {
        // TODO Auto-generated method stub
        System.out.println("sql server------------->查找出所有的部门");
        return null;
    }


}

更改DepartManager类:

package com.mq.class1.reflectdemo.biz;

import java.util.List;

import com.mq.class1.reflectdemo.dao.IDepart;
import com.mq.class1.reflectdemo.entity.Depart;
import com.mq.class1.reflectdemo.mysqldaoImpl.DepartService;

public class DepartManager {

    private IDepart dao = null;

    /**
     * 在构造方法中传递进来一个接口Idepart,可以自由的进行dao层的转换
     * 
     * @param dao
     */
    public DepartManager(IDepart dao) {
        this.dao = dao;
    }

    public Depart getDepartById(int id) {
        dao.getDepartById(id);
        return null;
    }

    public List getAllDepart() {
        // TODO Auto-generated method stub
        dao.getAllDepart();
        return null;
    }
}

Test类做相应的改变:

package com.mq.class1.reflectdemo.view;

import com.mq.class1.reflectdemo.biz.DepartManager;
import com.mq.class1.reflectdemo.dao.IDepart;
import com.mq.class1.reflectdemo.mysqldaoImpl.DepartService;

public class Test {

    public static void main(String[] args) {
        IDepart mysqlDao = new DepartService();
        DepartManager departManager = new DepartManager(mysqlDao);
        // 调用biz层中DepartManager类的getDepartById方法和getAllDepart方法
        departManager.getDepartById(1);
        departManager.getAllDepart();

        IDepart sqlserverDao = new com.mq.class1.reflectdemo.sqlserverdaoImpl.DepartService();
        departManager = new DepartManager(sqlserverDao);
        // 调用biz层中DepartManager类的getDepartById方法和getAllDepart方法
        departManager.getDepartById(1);
        departManager.getAllDepart();

    }
}

输出结果:
mysql————->根据编号1,可以查找出相应的部门
mysql————->查找出所有的部门
sql server————->根据编号1,可以查找出相应的部门
sql server————->查找出所有的部门

第三版本:

为了让界面层看起来更加的简单,对代码进行了如下的操作
1.使用工厂模式,创建dao层
2.达到在界面层输入好使用的数据库类型,就可以使用这种类型的数据库

结构目录:
这里写图片描述

AppType.java

package com.mq.class1.reflectdemo.basetype;

public enum AppType {

    sqlserver, mysql, oracle
}

Factory:

package com.mq.class1.reflectdemo.factory;

import com.mq.class1.reflectdemo.basetype.AppType;
import com.mq.class1.reflectdemo.dao.IDepart;
import com.mq.class1.reflectdemo.sqlserverdaoImpl.DepartService;

public class Factory {

    private static Factory factory = null;
    private static IDepart dao = null;

    public static Factory getInstance() {
        if (factory == null) {
            factory = new Factory();
        }
        return factory;
    }

    /**根据不同的类型创建相应的dao层
     * @param type
     * @return
     */
    public IDepart createDepart(AppType type) {
        switch (type) {
        case sqlserver:
            dao = new DepartService();
            break;
        case mysql:
            dao = new com.mq.class1.reflectdemo.mysqldaoImpl.DepartService();
            break;

        default:
            break;
        }
        return dao;
    }
}

更改DepartManager.java:

package com.mq.class1.reflectdemo.biz;

import java.util.List;

import com.mq.class1.reflectdemo.basetype.AppType;
import com.mq.class1.reflectdemo.dao.IDepart;
import com.mq.class1.reflectdemo.entity.Depart;
import com.mq.class1.reflectdemo.factory.Factory;
import com.mq.class1.reflectdemo.mysqldaoImpl.DepartService;

public class DepartManager {

    private IDepart dao = null;
    private Factory factory = null;

    /**
     * 在构造方法中传递进来一个枚举类型的参数,可以根据参数创建相应的dao层
     * 
     * @param dao
     */
    public DepartManager(AppType type) {
        factory = new Factory();
        this.dao = factory.createDepart(type);
    }

    public Depart getDepartById(int id) {
        dao.getDepartById(id);
        return null;
    }

    public List getAllDepart() {
        // TODO Auto-generated method stub
        dao.getAllDepart();
        return null;
    }
}

修改Test.java,界面更加简单:

package com.mq.class1.reflectdemo.view;

import com.mq.class1.reflectdemo.basetype.AppType;
import com.mq.class1.reflectdemo.biz.DepartManager;


public class Test {

    public static void main(String[] args) {
        //改变AppType.sqlserver或者AppType.mysql可以切换两个数据库
        DepartManager departManager = new DepartManager(AppType.sqlserver);
        departManager.getDepartById(1);
        departManager.getAllDepart();
    }
}

第四版本:

第三版本虽然已经充分体现了高内聚低耦合的特点,但是如果要新增一个数据库,就会在DepartManager文件里添加相应的代码,要重新进行编译,如果量比较大的话则速度很慢。所以进行了一下的更改,使用配置文件的方式。新增加xml文件。如下
config.xml:



    
        mysql
      com.mq.class1.reflectdemo.mysqldaoImpl
    
    
        sqlserver
    com.mq.class1.reflectdemo.sqlserverdaoImpl
    

要达到这样的效果,只需要更改Factory.java文件,如下:

package com.mq.class1.reflectdemo.factory;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.util.InvalidPropertiesFormatException;
import java.util.List;
import java.util.Properties;

import org.dom4j.Document;
import org.dom4j.DocumentException;
import org.dom4j.Element;
import org.dom4j.io.SAXReader;

import com.mq.class1.reflectdemo.basetype.AppType;
import com.mq.class1.reflectdemo.dao.IDepart;
import com.mq.class1.reflectdemo.sqlserverdaoImpl.DepartService;

public class Factory {

    private static Factory factory = null;
    private static IDepart dao = null;

    public static Factory getInstance() {
        if (factory == null) {
            factory = new Factory();
        }
        return factory;
    }

    /**
     * 根据不同的类型创建相应的dao层
     * 
     * @param type
     * @return
     */
    public IDepart createDepart() {
        String myPackage = getTypeFromXML();
        String className = myPackage + ".DepartService";
        IDepart dao = null;
        try {
            Class class1 = Class.forName(className);
            dao = (IDepart) class1.newInstance();
        } catch (ClassNotFoundException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (InstantiationException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (IllegalAccessException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }

        return dao;
    }

    /**
     * 使用dom4j或者其他的解析工具,将package里的 文本解析出来,不懂得可以查看我的一篇关于demo4j的博客,很简单的一个
     * 
     * @return
     */
    public String getTypeFromXML() {
        SAXReader reader = new SAXReader();
        Document document = null;
        try {
            document = reader
                    .read(new File(
                            "E:\\Workspaces\\MyEclipse 10\\Test\\src\\com\\mq\\class1\\config.xml"));
        } catch (DocumentException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
        Element root = document.getRootElement();
        String mypackage = "";
        // 查找name为mysql的包路径,用到XPath知识
        List elements = root.selectNodes("basic[name=&#39;sqlserver&#39;]");//在此更改要使用的数据库名字,xml文件会自动的找到路径,不存在重新编译的问题
        for (Element element : elements) {
            mypackage = element.elementText("package");
        }
        return mypackage;
    }
}
相关文章
最新文章
热点推荐