前言:

  在我们还没学习框架之前,肯定都学过JDBC。百度百科对JDBC是这样介绍的【JDBC(Java DataBase Connectivity,java数据库连接)是一种用于执行SQL语句的Java API,可以为多种关系数据库提供统一访问,它由一组用Java语言编写的类和接口组成。JDBC提供了一种基准,据此可以构建更高级的工具和接口,使数据库开发人员能够编写数据库应用程序,同时,JDBC也是个商标名。】通过JDBC我们可以完成Java对关系型数据库的SQL操作。下面我们介绍的这种模式是JDBC中使用的设计模式。

一、定义

  将抽象部分与它的具体实现部分分离,使他们都可以独立地变化。是通过组合方式建立两个类之间的联系,而不是继承

二、适用场景

1、抽象和具体实现之间增加更多灵活性

  使用桥接模式可以避免在这两个之间建立静态的继承关系,而是去建立组合关系。

2、一个类存在两个(或多个)独立变化的维度,且这两个维度需要独立进行扩展

  对于桥接模式可以这样理解,桥接就像一座桥,可以用来连接两个不同地方,这两个地方自由发展,中间的贸易是通过一座桥来连接。

3、不希望使用继承,或者是由于多层继承导致系统类的个数剧增

  同第一点理解

三、JDBC中的桥接模式

  首先我们弄清楚桥接模式中需要什么角色:

  1、实现类接口

  2、抽象类

  3、实现接口类

  4、继承抽象类

我们来看一下大概的图是怎么样的

  从图中我们能很清楚的看到抽象类和接口之间是通过组合方式来关联,这样关联有什么好处呢?抽象类下面可以自行发展自己的子类,并且接口类也可以自己发展子类。两者之间互不影响。这正是我们上面所说的两个维度独立扩展。不要以为客户端只能调用使用抽象类,而是接口下面的实现类可以放入抽象类的子类中进行操作。大致了解完之后,JDBC中又是怎么实现桥接模式的呢?

  我们对Driver接口一定不陌生。如果从桥接模式来看,Driver就是一个接口,下面可以有MySQL的Driver,Oracle的Driver,这些就可以当做实现接口类。那么我们现在来看看MySQL中的Driver类

public class Driver extends NonRegisteringDriver implements java.sql.Driver {
public Driver() throws SQLException {
} static {
try {
DriverManager.registerDriver(new Driver());
} catch (SQLException var1) {
throw new RuntimeException("Can't register driver!");
}
}
}

特别简短的代码,其实只调用了DriverManager中的registerDriver方法来注册驱动。当驱动注册完成后,我们就会开始调用DriverManager中的getConnection方法了

public class DriverManager {
public static Connection getConnection(String url,
String user, String password) throws SQLException {
java.util.Properties info = new java.util.Properties(); if (user != null) {
info.put("user", user);
}
if (password != null) {
info.put("password", password);
} return (getConnection(url, info, Reflection.getCallerClass()));
} private static Connection getConnection(
String url, java.util.Properties info, Class<?> caller) throws SQLException {
/*
* When callerCl is null, we should check the application's
* (which is invoking this class indirectly)
* classloader, so that the JDBC driver class outside rt.jar
* can be loaded from here.
*/
ClassLoader callerCL = caller != null ? caller.getClassLoader() : null;
synchronized(DriverManager.class) {
// synchronize loading of the correct classloader.
if (callerCL == null) {
callerCL = Thread.currentThread().getContextClassLoader();
}
} if(url == null) {
throw new SQLException("The url cannot be null", "08001");
} println("DriverManager.getConnection(\"" + url + "\")"); // Walk through the loaded registeredDrivers attempting to make a connection.
// Remember the first exception that gets raised so we can reraise it.
SQLException reason = null; for(DriverInfo aDriver : registeredDrivers) {
// If the caller does not have permission to load the driver then
// skip it.
if(isDriverAllowed(aDriver.driver, callerCL)) {
try {
println(" trying " + aDriver.driver.getClass().getName());
Connection con = aDriver.driver.connect(url, info);
if (con != null) {
// Success!
println("getConnection returning " + aDriver.driver.getClass().getName());
return (con);
}
} catch (SQLException ex) {
if (reason == null) {
reason = ex;
}
} } else {
println(" skipping: " + aDriver.getClass().getName());
} } // if we got here nobody could connect.
if (reason != null) {
println("getConnection failed: " + reason);
throw reason;
} println("getConnection: no suitable driver found for "+ url);
throw new SQLException("No suitable driver found for "+ url, "08001");
} }
}

  上面是简化的代码,可以看到需要返回的是Connection对象。在Java中通过Connection提供给各个数据库一样的操作接口,这里的Connection可以看作抽象类。可以说我们用来操作不同数据库的方法都是相同的,不过MySQL有自己的ConnectionImpl类,同样Oracle也有对应的实现类。这里Driver和Connection之间是通过DriverManager类进行桥接的,不是像我们上面说的那样用组合关系来进行桥接。

四、总结

  桥接模式其实特别好理解,只需要看一眼上面的UML类图,也许你就知道桥接模式的使用方法。JDBC这里使用桥接模式可以让Driver和Connection下面的类根据不同数据库来实现不同的发展。就像我们适用场景中的第二点。当然正如我们标题所说的结合着JDK源码来看设计模式。也许看完这篇博客你有自己的理解JDBC这里为什么要用桥接模式。

结合JDK源码看设计模式——桥接模式的更多相关文章

  1. 结合JDK源码看设计模式——原型模式

    定义: 指原型实例指定创建对象的种类,并且通过拷贝这些原型创建新的对象.不需要知道任何创建的细节,不调用构造函数适用场景: 类初始化的时候消耗较多资源 new产生的对象需要非常繁琐的过程 构造函数比较 ...

  2. 结合JDK源码看设计模式——模板方法模式

    前言: 相信很多人都听过一个问题:把大象关进冰箱门,需要几步? 第一,把冰箱门打开:第二,把大象放进去:第三,把冰箱门关上.我们可以看见,这个问题的答案回答的很有步骤.接下来我们介绍一种设计模式--模 ...

  3. 结合JDK源码看设计模式——迭代器模式

    前言: Iterator翻译过来就是迭代器的意思.在前面的工厂模式中就介绍过了iterator,不过当时介绍的是方法,现在从Iterator接口的设计来看,似乎又是一种设计模式,下面我们就来讲讲迭代器 ...

  4. 结合JDK源码看设计模式——建造者模式

    概念: 将一个复杂对象的构建与它的表示分离.使得同样构建过程可以创建不同表示适用场景: 一个对象有很多属性的情况下 想把复杂的对象创建和使用分离 优点: 封装性好,扩展性好 详解: 工厂模式注重把这个 ...

  5. 结合JDK源码看设计模式——策略模式

    前言: 现在电商已经成为我们生活中不可或缺的购物渠道,同时各大商家会针对不同的时间做出不同的折扣,这在我们看来就是一种营销手段,也是一种策略,今天我们就来讲讲JDK中的策略模式是怎么样的. 一.定义 ...

  6. 结合JDK源码看设计模式——组合模式

    前言: 相信大家都打开过层级很多很多的文件夹.如果把第一个文件夹看作是树的根节点的话,下面的子文件夹就可以看作一个子节点.不过最终我们寻找的还是文件夹中的文件,文件可以看做是叶子节点.下面我们介绍一种 ...

  7. 结合JDK源码看设计模式——单例模式

    定义: 保证一个类仅有一个实例,并提供一个全局访问点 适用场景: 确保任何情况下这个对象只有一个实例 详解: 私有构造器 单利模式中的线程安全+延时加载 序列化和反序列化安全, 防止反射攻击 结合JD ...

  8. 结合JDK源码看设计模式——简单工厂、工厂方法、抽象工厂

    三种工厂模式的详解: 简单工厂模式: 适用场景:工厂类负责创建的对象较少,客户端只关心传入工厂类的参数,对于如何创建对象的逻辑不关心 缺点:如果要新加产品,就需要修改工厂类的判断逻辑,违背软件设计中的 ...

  9. 结合JDK源码看设计模式——享元模式

    前言 在说享元模式之前,你一定见到过这样的面试题 public class Test { public static void main(String[] args) { Integer a=Inte ...

随机推荐

  1. [CVPR2017] Deep Self-Taught Learning for Weakly Supervised Object Localization 论文笔记

    http://openaccess.thecvf.com/content_cvpr_2017/papers/Jie_Deep_Self-Taught_Learning_CVPR_2017_paper. ...

  2. 队列Queue和栈

    1.队列Queue是常用的数据结构,可以将队列看成特殊的线性表,队列限制了对线性表的访问方式,只能从线性表的一段添加(offer)元素, 从另一段取出(poll)元素,队列遵循先进先出的原则. 2.J ...

  3. 能否使用require('.json')的方式加载大量JSON文件?

    Node.js中推崇非阻塞I/O,但是require一个模块时却是同步调用的,这会带来性能上的开销,但并不是每次require都很耗时,因为在require成功之后会缓存起来,在此加载时直接从缓存读取 ...

  4. shell 中各种括号的作用()、(())、[]、[[]]、{}

    一.小括号,圆括号 () 1.单小括号 () 命令组.括号中的命令将会新开一个子shell顺序执行,所以括号中的变量不能够被脚本余下的部分使用.括号中多个命令之间用分号隔开,最后一个命令可以没有分号, ...

  5. 【基于url权限管理 shiro(一)】--基础

    只要有用户参与的系统一般都要有权限管理,权限管理实现对用户访问系统的控制,按照安全规则或者安全策略控制用户可以访问而且只能访问自己被授权的资源.权限管理包括用户认证和授权两部分.   用户认证 1.概 ...

  6. Access Logging Tomcat

    73.6 Configure Access Logging server.tomcat.accesslog.buffered=true # Buffer output such that it is ...

  7. Spring Security 实战:QQ登录实现

    准备工作 1.在 QQ互联 申请成为开发者,并创建应用,得到APP ID 和 APP Key.2.了解QQ登录时的 网站应用接入流程.(必须看完看懂) 为了方便各位测试,直接把我自己申请的贡献出来:A ...

  8. MongoDB中文档操作(二)

    一.插入文档  1.db.集合名.insert()   插入一个:db.user.insert({name:"Join",age:13,address:"beijing& ...

  9. 拿到6个重磅offer的大神,超详细面试经验总结

    本人是国内某财经院校的小本,学校不算很有名,也没有很好的硬件条件,但是很幸运的在这样的就业大环境里拿了6个OFFER,其中包括一些股份制商业银行的总行,4大国有商业银行的省行,以及国内最一流国企的省公 ...

  10. web项目部署到本地tomcat时,运行tomcat的startup.bat一闪而过

    在eclipse里面启动tomcat时都是正常的,打成War包后,也无法自动解压,百度了好多方法均尝试失败,然后看到了下方的百度经验,配完环境变量后,tomcat可以正常启动了.如下为步骤: 1. 遇 ...