文档章节

从设计模式到实际应用

_Zuozuo
 _Zuozuo
发布于 2017/02/17 23:52
字数 2014
阅读 52
收藏 1

        一个好的设计模式,能让你少走许多弯路!你将有更多的时间来思考。

                                                                                        -------题要

        很早以前就知道设计模式,最近有比较多的提到设计模式。能说上来一些,但是具体的没有去深入的了解过,JAVA交流群里面经常有人问一些问题,许多问题看着能解决却说不出个所以然来。是故,花了些时间研究了一下JAVA里面的23种设计模式。

        其中前面几个讲的都是工厂模式以及工厂模式的进化。这个稍微多看了一下。现在的一个主流的思想就是把各个层次的东西降低耦合,甚至解耦。但是无论是多么好的东西,都会有他的缺点,比如解耦中用到的IOC控制反转就把对象创建速度减慢了至少一倍以上。虽然他并没有这么重要,但是不得不承认,过度的解耦是会对程序造成影响的,只是说,解耦的好处大于他造成的影响。springMVC把视图层,控制器,业务层,数据层解耦之后,由于层次的增加,必然使得一些简单的操作变得复杂起来,当然,对于大型项目,对于拓展性,解耦带来优势无可质疑。但是,在实际开发中,解耦带来的弊端也会显示出来。很多时候,我们进行一次开发,到达二次三次四次之后往往变得面目全非。第一次进行粗糙开发的时候,我觉得,要是我们能够以一个比较快的速度进行开发,快速展示数据,提供交互,将对项目的快速定型产生有利影响。而完全解耦限制了我们的一次开发速度。是故,有必要提供一些快速的访问代码建立项目的雏形。另外,提高代码的复用率也能够让项目看起来比较清爽,不会因为过多的过深的文件结构扰乱思绪。

        于此,以工厂设计模式思想为起点,改进了一下项目的代码。实现了一些基本的快速服务。当然,也得益与spring框架提供的热调试能力,即控制器或者业务层的代码修改不需要进行服务器的重启,比如TOMCAT,这可以大大减少我们开发的时间,如果运行5个项目,重启一次调试所需要的时间为2-4分钟。在热调试下,当即修改,当即生效。

  

数据持久层代码如下

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" 
	"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="PublicMapper">
	<!-- @author : online zuozuo -->
	<select id="findByTableName" parameterType="pd" resultType="pd">
		<if test="tableName != null  and tableName != ''">
			select * from ${tableName}
		</if>
	</select>

	<select id="listPageFindByTableName" parameterType="page"
		resultType="pd">
		<if test="pd.tableName != null  and pd.tableName != ''">
			select * from ${pd.tableName}
		</if>
	</select>

	<select id="findByIdAndTableName" parameterType="pd" resultType="pd">
		<if
			test="tableName != null  and tableName != '' and ID != null and ID != ''">
			<!-- 使用limit 1 是为了性能优化,减少数据库的压力,根据数据库工作原理,没有limit 1 的sql会去扫描全表,否则会在查询到记录后结束查询 -->
			select * from ${tableName} where ID=#{ID} limit 1
		</if>
	</select>

	<select id="findByFieldAndTableName" parameterType="pd"
		resultType="pd">
		<if test="tableName != null  and tableName != ''">
			select * from ${tableName}
		</if>
		<if test="key != null  and key != '' and value != null and value !=''">
			where ${key}=${value}
		</if>
	</select>

	<select id="listPageFindByFieldAndTableName" parameterType="pd"
		resultType="pd">
		<if test="pd.tableName != null  and pd.tableName != ''">
			select * from ${pd.tableName}
		</if>
		<if
			test="pd.key != null  and pd.key != '' and pd.value != null and pd.value !=''">
			where ${pd.key}=${pd.value}
		</if>
	</select>
</mapper>

 

业务层代码如下


package com.M.service.Public;

import java.util.List;

import javax.annotation.Resource;

import org.springframework.stereotype.Service;

import com.M.dao.DaoSupport;
import com.M.entity.Page;
import com.M.util.PageData;

/**
 * 
 * @author online zuozuo于2017年2月14日下午12:40:14编辑 提供给控制器的数据库基础服务
 *
 */

@Service("publicService")
public class PublicService {

	@Resource(name = "daoSupport")
	private DaoSupport dao;

	/**
	 * 通过表名查询全部信息
	 * 
	 * @param tableName
	 *            表名
	 */
	@SuppressWarnings("unchecked")
	public List<PageData> findByTableName(String tableName) throws Throwable {
		PageData pd = new PageData();
		pd.put("tableName", tableName);
		return (List<PageData>) dao.findForList("PublicMapper.findByTableName", pd);
	}

	/**
	 * 重载:通过表名查询全部信息 - 支持翻页
	 * 
	 * @param tableName
	 *            表名
	 * @param b
	 *            是否需要翻页
	 */
	@SuppressWarnings("unchecked")
	public List<PageData> findByTableName(String tableName, boolean b) throws Throwable {
		PageData pd = new PageData();
		pd.put("tableName", tableName);
		if (b) {
			Page page = new Page();
			page.setPd(pd);
			return (List<PageData>) dao.findForList("PublicMapper.listPageFindByTableName", page);
		} else {
			return (List<PageData>) dao.findForList("PublicMapper.findByTableName", pd);
		}

	}

	/**
	 * 通过ID和表名查询单条信息
	 * 
	 * @param tableName
	 *            表名
	 * @param key
	 *            ID
	 */
	public PageData findByIdAndTableName(String tableName, String key) throws Throwable {
		PageData pd = new PageData();
		pd.put("tableName", tableName);
		pd.put("ID", key);
		return (PageData) dao.findForObject("PublicMapper.findByIdAndTableName", pd);
	}

	/**
	 * 通过字段K,V对和表名查询信息
	 * 
	 * @param tableName
	 *            表名
	 * @param key
	 *            字段名
	 * @param value
	 *            字段值
	 */
	@SuppressWarnings("unchecked")
	public List<PageData> findByFieldAndTableName(String tableName, String key, String value) throws Throwable {
		PageData pd = new PageData();
		pd.put("tableName", tableName);
		pd.put("key", key);
		pd.put("value", value);
		return (List<PageData>) dao.findForList("PublicMapper.findByFieldAndTableName", pd);
	}

	/**
	 * 重载:通过字段和表名查询信息,map里面需要有一个K,V对来表示字段名和值名
	 * 
	 * @param tableName
	 *            表名
	 * @param key
	 *            字段名
	 * @param value
	 *            字段值
	 * @param b
	 *            是否需要支持翻页
	 */
	@SuppressWarnings("unchecked")
	public List<PageData> findByFieldAndTableName(String tableName, String key, String value, boolean b)
			throws Throwable {
		PageData pd = new PageData();
		pd.put("tableName", tableName);
		pd.put("key", key);
		pd.put("value", value);
		if (b) {
			Page page = new Page();
			page.setPd(pd);
			return (List<PageData>) dao.findForList("PublicMapper.listPageFindByFieldAndTableName", page);
		} else {
			return (List<PageData>) dao.findForList("PublicMapper.findByFieldAndTableName", pd);
		}

	}
}

 

        提供这几个服务有几种用处。

按照正常的流程,我们如果需要向用户展示某个表的全部数据,需要先写持久层,编写sql语句,取出数据,然后建立一个业务类和控制器类,接收该数据并返回给控制器,由控制器将数据返回给请求用户。实现这一个简单的步骤需要横跨数据持久层,业务层,控制器,视图层四个文件,并且面临一个问题,一旦sql编写有误,或者用户临时需要换另外一张表进行展示,需要重新编译发布到tomcat服务器,这是一个很费时的过程。还存在的另外一个问题是,程序中存在许多这样类似的查询,遍布在各个文件中,复用性并不是很好,甚至某些文件内容不但没有复用,而且重复写了多次。 不便于管理。此处提供一个公用的动态sql,以类似于反向工厂模式的利用。来实现一些快速的基础服务,(如果再进行扩展,就等于是把整个sql搬到了控制器,这是致命的,此处的目的是为了解决一些基本的问题,减少一些弊端,而不是为了重新耦合程序)由此,我们如果需要某张表的全部数据,只需要在控制器里面写一句代码即可!

另外,这样编写除了热变动之外,还是一个好处就是,对于一个库中的表的全查询以及该服务提供的简单功能代码能够在全程序中得到复用,另外由于分布在统一的两个文件中,不会产生较高的文件管理成本。基本上也不太需要维护。另外,用在管理系统中,由于没有并发问题以及较高的性能问题,该代码甚至不需要替换成优化的sql查询。可以直接放置在程序中使用。另一个,该代码进行了简单的优化,不需要做太多修改。

控制器代码如下:

			//可取得某张表的全部数据并置入list集合中。如果需要更换表名
			//只需改变参数tableName即可,并且不需要重启。
			List<PageData> list=publicService.findByTableName("tableName"):
				
			//如果上述记录需要支持翻页,则只需加一个ture即可	
			List<PageData> list=publicService.findByTableName("tableName",true):
					
			//如果需要获取某张表中单个ID的单条信息
			Object obj = publicService.findByIdAndTableName("tableName","1000005");
			
			//如果需要某表的字段KV对查询某表信息
			List<PageData> list=publicService.findByFieldAndTableName("tableName","key","value"):
				
			//如果通过KV对查询的信息需要翻页
			List<PageData> list=publicService.findByFieldAndTableName("tableName","key","value",true):

可能每次只会使用其中五种用法的一种,此处是展示该代码怎么用

© 著作权归作者所有

_Zuozuo

_Zuozuo

粉丝 5
博文 22
码字总数 14942
作品 0
杭州
后端工程师
私信 提问
Design Patterns In FE --- 工厂模式

示例代码地址: github.com/FatGe/Desig… 工厂模式 工厂,是构造方法的抽象,用来实现不同的分配方案。它所涉及三类模式,简单工厂模式、工厂方法模式、抽象工厂模式本质上都是为了实例化。...

Yzz
08/06
0
0
设计模式学习笔记十四:适配器模式、桥接模式与外观模式

1.适配器模式与桥接模式的区别和联系 适配器模式和桥接模式都是间接引用对象,因此可以使系统更灵活,在实现上都涉及从自身以外的一个接口向被引用的对象发出请求。 两种模式的区别在于使用场...

长平狐
2013/06/17
128
0
万能框架丨设计模式——策略模式

版权声明:欢迎转载,转载请注明出处 https://blog.csdn.net/weixin_38239050/article/details/88621100 策略模式 与工厂模式不同的是: 工厂模式是new对象 策略模式是处理策略,返回不同结果...

橙子va
03/17
0
0
【设计模式笔记】(十六)- 代理模式

一、简述 代理模式(Proxy Pattern),为其他对象提供一个代理,并由代理对象控制原有对象的引用;也称为委托模式。 其实代理模式无论是在日常开发还是设计模式中,基本随处可见,中介者模式中...

MrTrying
2018/06/24
0
0
简单工厂、工厂方法、抽象工厂、策略模式、策略与工厂的区别

转载:原地址http://www.cnblogs.com/zhangchenliang/p/3700820.html 简单工厂、工厂方法、抽象工厂、策略模式、策略与工厂的区别 结合简单示例和UML图,讲解工厂模式简单原理。 一、引子 话说...

法斗斗
2018/05/08
277
0

没有更多内容

加载失败,请刷新页面

加载更多

Dubbo-自适应拓展机制

背景 在 Dubbo 中,很多拓展都是通过 SPI 机制进行加载的,比如 Protocol、Cluster、LoadBalance 等,这些都是Dubbo的基础组件。这些基础组件的拓展不是在系统框架启动阶段被加载,而是拓展方...

rock-man
25分钟前
5
0
Kali安装fcitx输入法(五笔)

安装fcitx > sudo apt-get install fcitx-rime fcitx-config-gtk3 重启 > sudo reboot fcitx配置 效果就是这样 配置输入法切换 系统设置...

yeahlife
27分钟前
4
0
IE之css3效果兼容

本文转载于:专业的前端网站▷IE之css3效果兼容 一、兼容css阴影效果(ie滤镜) 1.Shadow,阴影 .shadow { -moz-box-shadow: 3px 3px 4px #000; -webkit-box-shadow: 3px 3px 4px #000; box-sha...

前端老手
30分钟前
4
0
NiushopB2C开源商城功能列表说明:

B2C单商户免费版:PC商城+微商城 B2C单商户标准版:PC商城+微商城组合套餐+阶梯优惠核销功能 B2C单商户企业版:PC商城+微商城拼团+组合套餐阶梯优惠+核销功能 B2C单商户分销版:PC商城+微商城...

niushop-芳
32分钟前
4
0
图片如何转GIF图片呢

如何将生活中拍摄的好玩有趣的图片制作成GIF动图呢?相信很多小伙伴都不知道要如何制作,其实制作方法非常的简单,下面分享一个图片转GIF动图的方法,希望这个方法能够帮助大家在与好友斗图时...

白米稀饭2019
39分钟前
4
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部