20145326 《Java程序设计》第9周学习总结

20145326 《Java程序设计》第9周学习总结

教材学习内容总结

第十六章

一、JDBC入门

1.JDBC简介

JDBC是用于执行SQL的解决方案,开发人员使用JDBC的标准接口,数据库厂商则对接口进行操作,开发人员无须接触底层数据库驱动程序的差异性,数据库本身是个独立运行的应用程序,你撰写的应用程序是利用通信协议对数据库进行指令交换,以进行数据的增删查找。通常你的应用程序会利用一组专门与数据库进行通信协议的链接库,以简化与数据库沟通时的程序撰写。有时候,更换数据库的需求并不是没有,应用程序跨平台也是经常的需求,JDBC基本上就是用来解决这些问题的。JDBC是Java联机数据库的标准规范。具体而言,它定义了一组标准类与接口,应用程序需要联机数据库时调用这组标准API,而标准API中的接口由数据库厂商操作,通常称为JDBC驱动程序。JDBC标准主要分为两个部分:JDBC应用程序开发者接口以及JDBC驱动程序开发者接口。如果你的应用程序需要联机数据库,就是调用JDBC应用程序开发者接口,相关API主要在java.sql与javax.sql两个包中,JDBC驱动程序开发者接口是数据库厂商操作驱动程序时的规范。如果有一段程序代码,它的作用是联机MySQL数据库,则需要在CLASSPATH中设定JDBC驱动程序,具体来说,就是在CLASSPATH中设定一个JAR文档,如果将来要换为Oracle数据库,只要置换Oracle驱动程序,具体来说就是在CLASSPATH改设为Oracle驱动程序的JAR文档,然而应用程序本身不用修改。JDBC希望达到的目的,是让Java程序设计员在撰写数据库操作程序时,可以有个统一的接口,无须依赖特定数据库的API,希望达到“写一个Java程序,操作所有数据库”的目的。厂商在操作JDBC驱动程序时,依操作方式可将驱动程序分为四种类型:(1)JDBC-ODBC Bridge Driver ,它是由Microsoft主导的数据库连接标准,基本上JDBC是参考ODBC制订而来,所以ODBC在Microsoft系统上最为成熟,不过由于JDBC与ODBC并未一一对应,所以部分调用无法直接转换,因此ODBC驱动程序本身也有跨平台限制。(2)Native API Driver,这个类型的驱动程序会以原生方式,调用数据库提供的原生链接库,在速度上是4种类型中最快的,但没有跨平台性。(3)JDBC-Net Driver,这类型的JDBC驱动程序会将JDBC方法调用转换为特定的网络协议调用,这种方式弹性高,具有跨平台性。(4)Native Protocol Driver ,这种方式可以跨平台,在效能上也有不错的表现,在不需要如(3)获得架构上的弹性时,通常会使用这种类型驱动程序,算是最常见的驱动程序类型。

 

2.连接数据库

为了要连接数据库系统,必须要有厂商操作的JDBC驱动程序,必须在CLASSPATH中设定驱动程序JAR文档。

3.使用Statement、ResultSet

Connection是数据库连接的代表对象,接下来要执行SQL的话,必须取得java.sql.Statement操作对象,它是SQL描述的代表对象。Statement的execute()可以用来执行SQL,并可以测试SQL是执行查询或更新,返回true表示SQL执行将返回ResultSet作为查询结果。视需求而定,Statement或者ResultSet在不使用时,可以使用close()将之关闭,以释放相关资源。Statement关闭时,所关联的ResultSet也会自动关闭。

4.使用PreparedStatement、CallableStatement

如果有些操作只是SQL语句当中某些参数会有所不同,其余的SQL子句皆相同,则可以使用java.sql.PreparedStatement。可以使用Connection的PreparedStatement()方法建立好预先编译的SQL语句,当中参数会变动的部分,先指定“?”这个占位字符。在JDBC里要表示日期,是使用java.sql.Date,其日期格式是“年、月、日”,要表示时间的话则是使用java.sql.Time,其时间格式为“时、分、秒”,如果要表示“时、分、秒、微秒”的格式,你可以使用java.sql.Timestamp。

二、JDBC进阶

1.使用ResultSet卷动、更新数据

在ResultSet时,默认可以使用next()移动数据光标至下一笔数据,而后使用getXXX()方法来取得数据。结果集类型可以指定3种设定:ResultSet.TYPEFORWARDONLY(默认)、ResultSet.TYPESCROLLINSENSITIVE、ResultSet.TYPESCROLLSENSITIVE。更新设定可以有两种指定:ResultSet.CONCURREADONLY(默认)、ResultSet.CONCUR_UPDATABLE。如果要使用ResultSet进行数据修改,则有些条件限制:必须选取单一表格、必须选取主键、必须选取所有NOT NULL的值。

2.批次更新

每一次执行executeUpdate(),其实都会向数据库发送一次SQL,如果大量更新的SQL有一万笔,就等于通过网络进行了一万次的信息传送,网络传送信息实际上必须打开I/O、进行路由等动作。所以最好就是所有收集的SQL,最后会串为一句SQL,然后传送给数据库,既然是批次更新,顾名思义,就是仅用在更新上,所以批次更新的限制是,SQL不能是SELECT,否则会抛出异常。

3.Blob与Clob

如果要将文档写入数据库,可以在数据库表格字段上使用BLOB或CLOB数据类型,BLOB用于存储大量二进制数据,像是图档、影音档等,CLOB用于存储大量的文字数据。

4.交易简介

交易的四个基本要求是原子性、一致性、隔离行为与持续性。当多个交易并行时,可能引发的数据不一致问题有哪些呢?(1)更新遗失:基本上就是指某个交易对字段进行更新的信息,因另一个交易的介入而遗失更新效力。(2)脏读:两个交易同时进行时,其中一个交易更新数据但未确认,另一个交易就读取数据,就有可能发生脏读问题。(3)无法重复的读取:某个交易两次读取同一字段的数据并不一致。(4)幻读:同一交易期间,读取到的数据笔数不一致。

5.metadata简介

Metadata即“诠读数据的数据”,数据库是用来存储数据的地方,然而数据库本身产品名称为何?数据库中有几个数据表格?表格名称为何?表格中有几个字段等?这些都是metadata。

6.RowSet简介

JDBC定义了java.sql.RowSet接口,用以代表数据的列集合,这里的数据并不一定是数据库中的数据,可以是电子表格数据、XML数据或任何具有列集合概念的数据源。RowSet定义了列集合基本行为,其下有JdbcRowSet、CachedRowSet、FilteredRowSet、JoinRowSet、WebRowSet五个标准列集合子接口。JdbcRowSet是联机式的RowSet,也就是操作JdbcRowSet期间,会保持与数据库的联机,可视为取得、操作ResultSet的行为封装,可简化JDBC程序的撰写,或作为JavaBean使用。CachedRowSet为脱机式的RowSet,在查询并填充完数据后,就会断开与数据源的联机,而不用占据相关联机资源,必要时也可以再与数据源联机进行数据同步。

第十七章

一、运用反射

1.反射

当我们使用一个类,如果这个类还未加载到内存中,系统会通过加载、连接、初始化对类进行初始化。

二、了解类加载器

1.类加载器层级架构

类加载指的是将类的class文件读入JVM,并为之创建一个Class对象。类连接指的是把类的二进制数据合并到JRE中,这又分为3个阶段:(1)校验:检查载入Class文件数据的正确性。(2)准备:给类的静态变量分配存储空间,并进行默认初始化。(3)解析:将类的二进制数据中的符号引用替换成直接引用。初始化指的是对类的静态变量、静态初始化块进行初始化。

注意:

a.一个final类型的静态属性,如果在编译时已经得到了属性值,那么调用该属性时,不会导致该类初始化,因为这个相当于使用常量。

b.使用ClassLoader()方法,只是加载该类,并未初始化。

类加载器就是负责将.class文件加载到内存中,并为之生成对应的java.lang.Class对象,它负责加载所有的类,而一旦一个类被加载入JVM中,就不会被再次载入了。在Java中,一个类用其全限定类名(即包名+类名)作为标识。JVM运行时会产生3个ClassLoader,分别为:BootstrapClassLoader(根类加载器)、ExtClassLoader(扩展类加载器)和AppClassLoader(系统类加载器)。

其中,BootstrapClassLoader负责加载JRE的核心类库,它不是ClassLoader的子类,使用C++编写,因此我们在Java中看不到它,通过其子类的getParent()方法获取时,将返回null,BootstrapClassLoader负责装载JRE目标下的rt.jar、charsets.jar等Java核心类库。

第十八章

一、自定义泛型

1.泛型

在JDK1.5版本之前,如果在集合中添加了不同类型的数据,需要在程序的运行期间对类型之间的转换进行检查。

例如:

List arrayList=new arrayList();

在arrayList中添加String类型的对象和Integer对象,但是我们定义如下一个数组 String[] values=new String[arrayList.size()]; 如果想要把arrayList转换成数组的话就会出现错误: arrayList.toArray(values);//运行期间错误。

这是因为List中包含了整型封装类型的对象。但是该错误只能在运行期间才能发现,程序能够正常的通过编译,并不会报错。对于程序中出现的错误,应该尽早的通知程序员。泛型能够很好地解决这个问题。

泛型在集合中的应用: 在JDK1.5版本之后Java提供了对泛型的支持。例如对于一个ArrayList列表来说,如果只想在列表中放入String类型元素,可以用下面的方法来实现: ArrayList list=new ArrayList();

泛型使得编译器能够在编译期间对集合中加入的对象进行检查,如果加入了不同类型的对象,就会报错,而不必等到运行期间再进行相关的类型转换。和原来没有使用泛型相比,它将原来需要在运行时期才能发现的异常提前到了编译期间,使得程序的安全性也大大提高,泛型一般用于集合类中。

二、枚举

1.枚举类型

枚举也是JDK1.5之后的版本以后Java新加入的特性。使用枚举可以表示一组常量数据。枚举的本质是一个类,可以使用enum关键字来声明一个枚举类型,其声明方式如下: [访问控制符] enum 枚举类型名{value1,value2,......} 使用枚举类型需要注意以下几点:

a.枚举类型可以定义在类的内部也可以定义在类的外部。如果定义在类的内部,那么其访问控制符可以是public,protected,private或者默认的控制符。如果定义在类的外部,其访·问控制符只能是public和默认控制符;

b.枚举类型中定义的value值都默认为public static final的。其值一经定义就不能在被修改了。多个value值之间需要用逗号隔开;

c.枚举类型中除了可以声明常量之外还可以声明方法。但是方法需要在常量之后,并且常量和方法之间要用分号区分;

d.枚举类型中的值可以通过枚举类型名直接对他们进行访问;

e.枚举类型不能声明为abstract或者final类型;

 

 

运行结果:

 

2.枚举类型的常用方法

public final String name()//返回枚举常量的名称; public final int ordinal()//返回枚举常量在枚举类型中的位置,第一个枚举值序号为0,依次类推; public String toString()//返回枚举常量的名字,可以重写此方法; public static valueOf(enumType,String name)//返回与name名字相对应的枚举常量;

 

运行结果:

三、注释

1.注释类型

在原始码中使用注释,对编译程序提供额外编译提示,或提供应用程序执行时期可读取的组态信息。注释可以仅用于原始码,编译后留在.class文档仅供编译程序读取或开放执行时期读取。

2.常用标准注释

@Override //就是标准注释,被注释的方法必须是父类或接口中已定义的方法,请编译程序协助是否真的为重新定义方法。 @Deprecated //如果某个方法原先存在与API中,后来不建议再使用,可以在该方法上注释。若有用户后续想调用或重新定义这个方法,编译程序会提出警告。对于支持泛型的API,建议明确指定泛型真正类型,如果没有指定,编译程序会提出警告。 @SuppressWarnings //指定抑制unchecked的警告产生: @SuppressWarnings(value={"unchecked"}) @SafeVarargs //表明开发人员确定避免了heap pollution问题。heap pollution问题就是编译程序无法检查执行时期的类型错误,无法具体确认自变量类型。 @FunctionalInterface //让编译程序可协助检查interface是否可做为lambda的目标类型 自定义注释类型 ·标示注释:就是注释名称本身就是信息,对编译程序或应用程序来说,主要是检查是否有注释出现,并作出对应的动作。 ·相关规则:

(1)如果注释名称本身无法提供足够信息,设置单值注释

(2)注释属性也可以用数组形式指定。

(3)在定义注释属性时,如果属性名称为value,则可以省略属性名称,直接指定值。

(4)对成员设定默认值,使用default关键字即可。

(5)要设定数组默认值,可以在default之后加上{},必要时{}中可放置元素值。

定义注释时,可使用java.lang.annotation.Target限定时可指定java.lang.annotation.ElementType的枚举值。 在制作JavaDoc文件时,默认不会将注释数据加入文件中,如果想要将注释数据加入文件,可以使用java.lang.annotation.Documented。 默认父类设定的注释,不会被继承至子类,在定义注释时,设定java.lang.annotation.Inherited注释,就可以让注释被子类继承。

3.JDK8标注增强功能

a.ElementType的枚举成员是用来限定哪个声明位置可以进行标注。在JDK8中,增加了两个枚举成员TYPE _PARAMETER、TYPE _USE。

b.ElementType.TYPE _ USE可用于标注在各式类型,一个标注如果被设定ElementType.TYPE_USE,只要是类型名称,都可以进行标注。

c.@Repeatable 可以让你在同一个位置重复相同标注

d.@Filters 作为收集重复标注信息的容器,而每个@Filters储存各自指定的字符串值。 执行时期读取注释信息

4.自定义注释

默认会将注释信息存储于.class文档,可被编译程序或位码分析工具读取,但执行时期无法读取注释信息,在执行时期读取注释信息,可以使用java.lang.annotation.Retention搭配java.lang.annotation.RetentionPolicy枚举指定。 RetentionPolicy为RUNTIME的时机,在于让注释在执行时期提供应用程序信息,可使用java.lang.reflect.AnnotatedElement接口操作对象取得注释信息。 JDK 8中新增了getDeclaredAnnotation()、getDeclaredAnnotationsByType()、getAnnotationsByType()三个方法。 getDeclaredAnnotation()可以让你取回指定的标注,在指定@Repeatable的标注时,会寻找收集重复标注的容器。 getDeclaredAnnotationsByType()、getAnnotationsByType()就不会处理@Repeatable的标记。

 

代码托管:

 

 

代码行数:

教材学习中的问题和解决过程

娄老师说本周任务是学习剩下的三章,哇塞,一转眼,厚厚的一本java书就学完了!虽说重点是16章,不过我还是抽时间把17章和18章看完了,有始有终嘛~时间是挤出来的,其实感觉还好,我就按着自己的节奏走,没想到一下子就顺利的将三章的内容都学了(不过重点还是放在16章的)。之前娄老师说过,java的核心内容是封装、继承、多态那部分知识,确实比较抽象难懂。之后的内容都是介绍各种API的应用,都是活生生的例子,比较具体,如果觉得难那是因为对这部分知识感到陌生,不熟悉。自己首先理清头绪,不懂的基础知识多看几遍书,然后再多敲几遍代码,仔细思考总结,将代码与知识点结合,感觉立马就上来了!要讲究科学的学习方法~不要盲目!!!

问题:对于教材509页的代码不是很理解,代码如下:

 

解决方法:Connection使用尝试自动关闭资源语法,所以执行完try区块后,Connection的close()就会被调用。

 

其他(感悟、思考等,可选)

虽说这周自学了三章,知识点比较多,但还好,没什么难点,就像娄老师之前说的,java的核心知识与难点之前都已经学完了,后面的章节全都是介绍一些类的应用。看第一遍教材的时候肯定觉得陌生,难以接受。这是个过程,很正常。在不断的学习中,我也在不断的寻找适合自己的好的学习方法。看第一遍教材先有个大概的了解,头脑里勾画出一个轮廓。然后看第二遍才是逐渐理解与体会,往轮廓里填内容,这时不能只看书,还要结合书上的代码,自己还要主动敲代码,主动发现问题。 第三遍是梳理知识点也是回忆,将大脑与知识相融合。这样下来对知识绝对会有进一步的掌握!自身也会有质的飞跃!要学会抓住重点,把力量用在刀刃上,寻找乐趣,保持激情,提高学习效率!现在的我是带着目的去看教材的,不是像以前那样盲目的。我后来发现这点尤其重要!我知道第16章、第17章和第18章跟之前一样,还是介绍一些类的应用,于是我采取和之前一样的办法,一边看书,一边总结,看书上总共介绍了多少种API,每一种API的架构是什么,每一种API的作用与注意事项是什么。就这样有系统的去学习,感觉效率十分高!而且头脑思绪清晰。娄老师课上强调了数据库这一章节内容的重要性,因为这部分知识与我们大三要学习的内容息息相关,于是我刻意的在16章花更多的时间,更仔细的敲代码,发现问题。其实这些知识不是难,我们只是感到陌生而已。同学们有了畏难情绪和厌学情绪,当然就学不进去了,还谈什么效率!这三章的知识不像之前的对象、封装、继承、多态那些概念那么抽象难懂,都是活生生的具体的例子,接受起来其实也挺快的。娄老师说的很对,重要的不是要你学多少java知识,而是通过不断的学习过程,来总结出一套适合自己的良好的学习方法,这将受用一生。当然不同的人肯定情况不一样,适合自己的才是最好的。时间用得多,不一定就学得好。找到属于自己的学习方法,提高效率!这比一切都重要!调整一下自己的心态吧,任何事情不要有畏难情绪,万事开头难,只要是对的,就坚持!最终一定会受益匪浅!!

学习进度条

  代码行数(新增/累积) 博客量(新增/累积) 学习时间(新增/累积) 重要成长
目标 3500行 20篇 300小时  
第一周 120/120 1/1 14/14  
第二周 340/460 1/2 14/28  
第三周 200/660 1/3 14/42  
第四周 320/980 1/4 14/56  
第五周 280/1260 1/5 14/70  
第六周 478/1738 2/7 16/86  
第七周 425/2163 2/9 16/102  
第八周 859/3022 3/12 16/118 学会用git托管代码,使用wc统计代码行数,重构
第九周 4482/7504 2/14 21/139 使用安卓开发平台~

posted on 2016-05-01 09:11  20145326蔡馨熠  阅读(442)  评论(6编辑  收藏  举报

导航