传统的使用jdbc来访问数据库的流程为:
Class.forName(“com.mysql.jdbc.Driver”);
String url = “jdbc:mysql://localhost:3306/test?user=root&password=123456″;
Connection con = DriverManager.getConnection(url);
Statement statement = con.createStatement();

最开始使用的时候,不明白为什么首先要加载一个驱动类,之后就可以取得了Connection了,很好奇DriverManager是怎么获得那个
驱动类的信息,后来看了下com.mysql.jdbc.Driver这个类的源代码,豁然开朗了。原来在com.mysql.jdbc.Driver类
中有这么一段静态初始化代码:
static {
try {
java.sql.DriverManager.registerDriver(new Driver());
} catch (SQLException E) {
throw new RuntimeException(“Can’t register driver!”);
}
}
也就是,在Class.forName加载完驱动类,开始执行静态初始化代码时,会自动新建一个Driver的对象,并调用DriverManager.registerDriver把自己注册到DriverManager中去。

ps1: Class.forName(String) 与ClassLoader.loadClass(String)的区别
Class.forName(String): 加载类,并且执行类初始化;可以通过Class.forName(String, boolean, ClassLoader)第二个参数来仅仅加载类不执行初始化;
ClassLoader.loadClass(String): 仅仅加载类,不执行类初始化;

ps2: 有时会看到这种用法:
Class.forName(“com.mysql.jdbc.Driver”).newInstance();
这是没有必要的,正如前述,静态初始化已经new了一个Driver的对象,注册到DriverManager中去,在此再建立一个Driver对象则是完全没有必要的,浪费空间。

ps3: 结合ps1,Class.forName(“com.mysql.jdbc.Driver”);相当于:
ClassLoader loader = Thread.currentThread().getContextClassLoader();
Class cls = loader.loadClass(“com.mysql.jdbc.Driver”);
cls.newInstance();
这种方法的问题同ps2, 浪费了一个Driver对象;

ps4: 在java 6中,引入了service
provider的概念,即可以在配置文件中配置service(可能是一个interface或者abstract
class)的provider(即service的实现类)。配置路径是:/META-INF/services/下面。详细信息见:http:
//docs.oracle.com/javase/6/docs/technotes/guides/jar/jar.html#Service%20Provider
而java.sql.DriverManager也添加了对此的支持,因此,在JDK6中,DriverManager的查找Driver的范围为:
1)system property “jdbc.drivers” 中配置的Driver值;
2)用户调用Class.forName()注册的Driver
3)service provider配置文件java.sql.Driver中配置的Driver值。

因此,在jdk6中,其实是可以不用调用Class.forName来加载mysql驱动的,因为mysql的驱动程序jar包中已经包含了
java.sql.Driver配置文件,并在文件中添加了com.mysql.jdbc.Driver.但在JDK6之前版本,还是要调用这个方法。

参考文档:
1)http://docs.oracle.com/javase/1.5.0/docs/api/java/sql/DriverManager.html
2)http://docs.oracle.com/javase/6/docs/api/index.html?java/sql/DriverManager.html
3)http://docs.oracle.com/javase/6/docs/technotes/guides/jar/jar.html#Service%20Provider

最新文章

  1. .net 之缓存
  2. RunTime的简单使用
  3. windows下codelite的使用
  4. SQL多条件查询安全高效比较
  5. 推荐一个大文件查找工具---WizTree
  6. java集合TreeMap应用---求一个字符串中,每一个字母出现的次数
  7. 2015 Multi-University Training Contest 1 题解&&总结
  8. iOS-UICollectionView自定义布局
  9. 清除Android工程中没用到的资源(转)
  10. 把VBScript的函数迁移到C#.NET
  11. Android开发之漫漫长途 番外篇——自定义View的各种姿势1
  12. 聊一聊顺序消息(RocketMQ顺序消息的实现机制)
  13. jade模版js中接收express的res.render
  14. 一键快速部署CodeBlocks的EGE图形库工具
  15. 海康JAVA SDK库动态路径加载
  16. 【20181025】win10下Python安装osmnx包
  17. IO 流小记录
  18. SpringMVC 接受页面传递参数
  19. PAT 乙级 1060 爱丁顿数(25) C++版
  20. QrenCode : 命令行下生成二维码图片

热门文章

  1. input 输入框type='search'去掉×
  2. 2017年8月9日学习内容存放 #socket通信介绍
  3. 其他pyton笔记
  4. JQuery--计算元素的宽度
  5. Eclipse安装FindBugs
  6. linux把普通用户添加到sudo组
  7. php 获取一张图片所有点的颜色值
  8. 2019.8.9 NOIP模拟测试15 反思总结
  9. 2019-3-1-安装-Sureface-Hub-系统-Windows-10-team-PPIPro-系统
  10. 错觉-Info:视错觉与UI元素间的可能