《疯狂java》我觉得是一本很好的java基础书,里面解释的比较通俗易懂,不繁琐,深入程度刚刚好,比较适合我现阶段来学习,巩固java基础知识,所以将所做的笔记整理如下:
1.数据类型分类:基本(8种---char实际上也是整型),引用,NULL 2.数组定义后空间就分配了,即使清空元素也会占用着空间 3.数组初始化: 静态初始化:int [] array=new int[]{1,22,33,55,75} 动态初始化:String[] books=new String[5] 动态初始化只需要指定数组长度,即为每个元素指定所需要的内存空间,系统将会根据数据类型自动分配初始值,分配规则如下: 基本类型(8种): byte short int long 默认值为0 float double 默认值为0.0 char 默认值为‘\u0000’ boolean 默认值是false 引用类型(类,接口,数组): 默认值是null 4.遍历数组: 首先,数组索引从0开始 除了传统的for(,,)循环遍历 现在可以使用增强for循环,如下: String[] books=new String{"三国",“水浒传”,“西游记”} for(String book:books){ //book="世说新语" System.out.println(book); } 注意:不要再这个循环里面给book赋值 //book="世说新语" 因为增强for循环是采用临时变量存储输出结果,赋值会有问题的。 5.数组是一种引用类型:数组对象存在 堆 里面,引用存在 栈 里面 6.操作数据的工具类是Arrays,包括copy(),sort(),toString()等方法,具体查阅API 7.this关键字总是指向调用该方法的对象,有两种情况: 一:构造方法里面 二:方法中引用调用该方法的对象 public class Dog{ public void eat(){ } public void jump(){ //不用通过new Dog对象,对象 点 的方式调用eat()方法 、 this其实在此可以省略 this.eat(); } } 8.static修饰的方法不能访问不使用static修饰的普通成员 9.static修饰的方法属于类本身,通过类调用或者new Object(不建议) 非static修饰的普通方法则属于类的对象 10.同一个类的一个方法调用另一个方法,本质上还是this或者类名 点 静态方法 形式。 如果是普通方法,那么就是this调用。如果是静态方法,那么就是默认使用类作为调用者 方法只是类和对象的附属,不是独立存在的 11.java方法的传递是值传递: 基本数据类型:
引用数据类型:因为传递的是对象的引用然而这个(拷贝过去的)引用实际操作的还是这个对象 所以这个和基本数据类型的结果是不一样的,但是都是值传递!!!
12. 递归算法:一个方法体内调用它自身,被称为方法递归,递归方法是一种隐式的循环,会重复执行某段代码,但是这种重复不需要循环控制。 递归要向已知方向递归,否则就成了无穷递归(死循环) 递归满足2个条件: 1)有反复执行的过程(调用自身) 2)有跳出反复执行过程的条件(递归出口) //斐波那契 long Fib(int n) { if (n == 0) return 0; if (n == 1) return 1; if (n > 1) return Fib(n-1) + Fib(n-2); }
13.成员变量和局部变量:
成员变量初始化可以赋默认值(比如 int 默认是数字0) 而局部变量除了形参外必须要显式的初始化(赋值) 还要注意成员变量和局部变量的生命周期,作用域。
java允许局部变量和成员变量同名:如果重名,那么局部变量会覆盖成员变量,如果想调用成员变量,那么可以使用this关键字来调用,不过我们应该避免这种情况!
14.我们调用静态成员变量的时候请直接用 类名.静态变量 的形式 ,而不要new 对象的形式,而普通的类变量要通过new 对象的形式调用。
15.与成员变量(放在堆内存中)不同,局部变量不属于任何类或者实例,所以局部变量保存在其方法的栈内存中。
16.访问权限修饰符
17.super关键字调用父类的method(继承关系的子类调用父类被重写的方法或者父类的filed)
18.super关键字调用父类的field
19.创建任何对象总是从该类继承树最顶层的构造器开始。
20.java的引用变量有两个类型:编译时类型(声明该变量时类型决定),运行时类型(实际赋给变量的对象决定) 多态:向上造型(父类引用指向子类对象)的时候如果子类重写了父类方法那么引用调用的方法就是子类重写的
21.instanceof关键字:通常前一个是引用类型变量,后一个是类 或者接口 Object hello="hello" if( hello instanceof String){ }
22.继承增强了重用但是破坏了封装
23.八种基本数据类型不符合面向对象思想,所以有了封装类,int Integer char Character 其余的都是首字母大写。 除了Character外,其他7种都可以同构传入参数构建包装类对象。 例如:Integet i=new Integer(5);
xxxValue(),比如intValue() floatValue()用于获取包装类的基本类型变量 获取包装类中的基本数据类型变量:
自动拆装箱: 自动装箱------基本类型--->包装类型 自动拆箱------包装类型--->基本类型
封装类的parseXxx()方法 字符串类型 转换为 基本类型 String类的valueOf()把 基本类型 转化成 字符串
例如:
24.封装类的数据比较问题: Integer a=2; Integer b=2; a==b 输出true
Integer c=128; Integer d=128; c==d 输出false 原因是Integer缓存封装了一个长度256范围-128到正127的数组,2在这个范围内,而正128已经超过了正127,这时候Integer c=128和Integer d=128都是属于new创建了对象,比较结果自然不同。
从java7开始可以用封装类的静态方法compare(xx,xx)来比较基本类型,包括Boolean,例如:Boolean.compare(true,false);
25.toString(); Person p=new Person(); 没有重写toString()的情况下直接输出System.out.pritln(p)是等价于System.out.pritln(p.toSting())的,这个是默认继承Object的方法。会打印出“类名+@+hashCode”的值 重写toString()后,才可以实现输出具有描述作用的信息,比如p对象里面的具体属性值。
26.==和equals()方法
27.第六章没有细看 后续补上
28.数学运算:float double数学运算会精度丢失,所以要用bigDecimal类,使用BigDecimal并且一定要用String来构造
但是想像一下吧,如果我们要做一个加法运算,需要先将两个浮点数转为String,然后够造成BigDecimal,在其中一个上调用add方法,传入另一个作为参数,然后把运算的结果(BigDecimal)再转换为浮点数。你能够忍受这么烦琐的过程吗?下面我们提供一个工具类Arith来简化操作。它提供以下静态方法,包括加减乘除和四舍五入: public static double add(double v1,double v2) public static double sub(double v1,double v2) public static double mul(double v1,double v2) public static double div(double v1,double v2) public static double div(double v1,double v2,int scale) public static double round(double v,int scale)
- import java.math.BigDecimal;
- /**
- * 进行BigDecimal对象的加减乘除,四舍五入等运算的工具类
- * @author ameyume
- *
- */
- public class Arith {
- /**
- * 由于Java的简单类型不能够精确的对浮点数进行运算,这个工具类提供精
- * 确的浮点数运算,包括加减乘除和四舍五入。
- */
- //默认除法运算精度
- private static final int DEF_DIV_SCALE = 10;
- //这个类不能实例化
- private Arith(){
- }
- /**
- * 提供精确的加法运算。
- * @param v1 被加数
- * @param v2 加数
- * @return 两个参数的和
- */
- public static double add(double v1,double v2){
- BigDecimal b1 = new BigDecimal(Double.toString(v1));
- BigDecimal b2 = new BigDecimal(Double.toString(v2));
- return b1.add(b2).doubleValue();
- }
- /**
- * 提供精确的减法运算。
- * @param v1 被减数
- * @param v2 减数
- * @return 两个参数的差
- */
- public static double sub(double v1,double v2){
- BigDecimal b1 = new BigDecimal(Double.toString(v1));
- BigDecimal b2 = new BigDecimal(Double.toString(v2));
- return b1.subtract(b2).doubleValue();
- }
- /**
- * 提供精确的乘法运算。
- * @param v1 被乘数
- * @param v2 乘数
- * @return 两个参数的积
- */
- public static double mul(double v1,double v2){
- BigDecimal b1 = new BigDecimal(Double.toString(v1));
- BigDecimal b2 = new BigDecimal(Double.toString(v2));
- return b1.multiply(b2).doubleValue();
- }
- /**
- * 提供(相对)精确的除法运算,当发生除不尽的情况时,精确到
- * 小数点以后10位,以后的数字四舍五入。
- * @param v1 被除数
- * @param v2 除数
- * @return 两个参数的商
- */
- public static double div(double v1,double v2){
- return div(v1,v2,DEF_DIV_SCALE);
- }
- /**
- * 提供(相对)精确的除法运算。当发生除不尽的情况时,由scale参数指
- * 定精度,以后的数字四舍五入。
- * @param v1 被除数
- * @param v2 除数
- * @param scale 表示表示需要精确到小数点以后几位。
- * @return 两个参数的商
- */
- public static double div(double v1,double v2,int scale){
- if(scale<0){
- throw new IllegalArgumentException(
- "The scale must be a positive integer or zero");
- }
- BigDecimal b1 = new BigDecimal(Double.toString(v1));
- BigDecimal b2 = new BigDecimal(Double.toString(v2));
- return b1.divide(b2,scale,BigDecimal.ROUND_HALF_UP).doubleValue();
- }
- /**
- * 提供精确的小数位四舍五入处理。
- * @param v 需要四舍五入的数字
- * @param scale 小数点后保留几位
- * @return 四舍五入后的结果
- */
- public static double round(double v,int scale){
- if(scale<0){
- throw new IllegalArgumentException(
- "The scale must be a positive integer or zero");
- }
- BigDecimal b = new BigDecimal(Double.toString(v));
- BigDecimal one = new BigDecimal("1");
- return b.divide(one,scale,BigDecimal.ROUND_HALF_UP).doubleValue();
- }
- /**
- * 提供精确的类型转换(Float)
- * @param v 需要被转换的数字
- * @return 返回转换结果
- */
- public static float convertsToFloat(double v){
- BigDecimal b = new BigDecimal(v);
- return b.floatValue();
- }
- /**
- * 提供精确的类型转换(Int)不进行四舍五入
- * @param v 需要被转换的数字
- * @return 返回转换结果
- */
- public static int convertsToInt(double v){
- BigDecimal b = new BigDecimal(v);
- return b.intValue();
- }
- /**
- * 提供精确的类型转换(Long)
- * @param v 需要被转换的数字
- * @return 返回转换结果
- */
- public static long convertsToLong(double v){
- BigDecimal b = new BigDecimal(v);
- return b.longValue();
- }
- /**
- * 返回两个数中大的一个值
- * @param v1 需要被对比的第一个数
- * @param v2 需要被对比的第二个数
- * @return 返回两个数中大的一个值
- */
- public static double returnMax(double v1,double v2){
- BigDecimal b1 = new BigDecimal(v1);
- BigDecimal b2 = new BigDecimal(v2);
- return b1.max(b2).doubleValue();
- }
- /**
- * 返回两个数中小的一个值
- * @param v1 需要被对比的第一个数
- * @param v2 需要被对比的第二个数
- * @return 返回两个数中小的一个值
- */
- public static double returnMin(double v1,double v2){
- BigDecimal b1 = new BigDecimal(v1);
- BigDecimal b2 = new BigDecimal(v2);
- return b1.min(b2).doubleValue();
- }
- /**
- * 精确对比两个数字
- * @param v1 需要被对比的第一个数
- * @param v2 需要被对比的第二个数
- * @return 如果两个数一样则返回0,如果第一个数比第二个数大则返回1,反之返回-1
- */
- public static int compareTo(double v1,double v2){
- BigDecimal b1 = new BigDecimal(v1);
- BigDecimal b2 = new BigDecimal(v2);
- return b1.compareTo(b2);
- }
- }
29.处理日期的类: Date类过时了,不推荐 目前用Calendar类:Calendar是抽象类,所以不能用构造器来创建其对象,它提供了几个静态的getInstance()方法来获取Calendar对象。
Calendar的月份是从0开始的:
常用方法:
add和roll区别:add可以进位(2013年6月加8月变成2014年2月,相反,roll就不行)
30.正则表示式这块内容用的时候直接翻资料,不用记忆。
集合框架
31.首先JAVA中循环遍历list有三种方式for循环、增强for循环(也就是常说的foreach循环)、iterator遍历,这里讨论的是itertor遍历 Iterator的三个方法: boolean hasNext(); Object next(); void remove();(无参数!!!)
Iterator迭代输出集合的demo:
注意: 1.it.next()方法返回的是Object类型。 2.删除元素要用迭代器这种,而不是for循环(删除后长度发生改变了) 3.赋值其实并未改变集合本身
Iterator必须依赖于集合对象
异常:
这里的“某个特定元素”意思是:上图的book.equals("疯狂Android讲义"),这就是特定的元素。
public static void main(String[] args) { // TODO Auto-generated method stub List<String> a=new ArrayList<String>(); a.add("a"); a.add("b"); a.add("c"); a.add("c"); a.add("c"); a.add("d"); a.add("e"); Iterator<String> iterator=a.iterator(); while (iterator.hasNext()) { String empString=(String)iterator.next(); if("c".equals(empString)){ iterator.remove(); } } /*for(String emp:a){ if("e".equals(emp)){ a.remove(emp); } }*/ System.out.println(a); }
32.foreach遍历
List<String> a=new ArrayList<String>(); a.add("a"); a.add("b"); a.add("c"); a.add("c"); a.add("c"); a.add("d"); a.add("e"); for(Object o:a){ if(o.equals("e")){ a.remove(o); //break; } } System.out.println(a); 加了break就不报错误信息ConcurrentModificationException,这种方法通常不使用,用迭代器删除最安全。
Set 33.Set集合无序不重复,就像一个“罐子”,丢进去的元素没有哦明显的顺序。 set添加对象比较的不是用==比较引用地址,而是用equals()比较,只要equals比较为true就不能添加:
34.set的主要实现类:hashSet 简而言之:hashset常用来在里面存储对象,而且这个对象必须要重写hashcode和equals方法。 特点:1.不能保证元素的排列顺序(本身set也是“无序”不重复的) 2.集合元素可以使null 3.hashSet判断两个元素相等的标准时两个对象通过equals()方法比较相等并且hashCode比较也相等!。
hashCode的好处以及作用:
List 35.List(常用,重头戏)有序,可重复的集合 常用API: 增:add(一个对象或元素) addAll(添加一个包含多个元素的集合) 删:remove(传入Index) 改:set subList 查:get indexOf lastIndexOf
36.List判断两个对象相等只要通过equals比较为true即可 37.ArrayList和Vector最主要的区别是ArrayList是线程不安全的,还有就是Vector是比较老的,现在一般不用。 38.Arrays(数组------>集合List)工具类的asList需要注意的地方(不可增加删除,固定长度!) 39.LinkedList和ArrayList,ArrayDeque的不同,主要区别是:ArrayList,ArrayDeque内部是基于数组形式来保存数据,所以访问(查询)快,而LinkedList(双端队列,栈)内部基于链表,插入,删除元素时性能出色。Vector也是基于数组但实际线程同步所以各方面性能下降。(但是数组的随机访问性能是最好的,比list还好------list是基于数组)
Map 40.map里面的key实际上高度类似Set,无序,不能重复
41.从源码上看,java是先实现了map,然后通过包装一个所有value都为null的map就实现了set集合
42.map里面的所有value其实类似一个List,可以重复,可以根据key索引来查找。
43.map封装了一个内部类Entry,该类封装了一个key-value对,entry包含了如下三个方法。 getKey,getValue,setValue
44.两个主要实现类HashMap和HashTable(自动重写了toString,打印的话输出key=value,key=value的形式) 对比: 1.HashTable线程安全,HashMap线程不安全 2.HashTable不允许把null值做为key和value,会引起NP异常,HashMap允许把null值做未来key和value,但是注意key是不能重复的,所以只能有一个key为null,但是value不管多少个都是可以为null的。
45.HashMap,HashTable比较key(用作key的对象必须实现equals何hashCode方法)和value的标准 不要使用可变对象作为Key,会引起访问问题
46.map实现类的性能分析
Collections工具类 47.常用方法:reverse sort swap
泛型 48.泛型需要注意的是List<String>并不是List<Object>的子类。
MYSQL与JDBC编程: 49.sun提供的JDBC可以完成的三个基本工作:
50.SQL知识: Mysql安装请自己百度。 mysql数据库的一个实例(Server instance)可以同时包含多个数据库。
数据库以及表基础 51.SQL语句基础: SQL(结构化查询语言)分为:查询语句,DML(数据操作 增删改) DDL(数据定义 创建create 修改alter 删除 drop和truncate------比较特殊,后续介绍) DCL(数据控制 授权grant revoke) 事务控制(commit rollback savepoint) sql语句的关键词不区分大小写
52.DDL 先看几个概念:表,数据字典,约束,视图,索引等。。。
创建表:
修改表 alter: sql语句中的字符串不是双引号,是单引号!!! 添加字段的语法:alter table tablename add (column datatype [default value][null/not null],….); 修改字段的语法:alter table tablename modify (column datatype [default value][null/not null],….); 删除字段的语法:alter table tablename drop (column); 添加、修改、删除多列的话,用逗号隔开。 使用alter table 来增加、删除和修改一个列的例子。
删除表(drop和truncate): drop table tableName;表结构被删除、表对象不复存在/表里面所有数据被删除/表的索引约束也被删除。 truncate只删除数据,保留表结构,而且只能一次性删除整个表的全部记录
数据库相关 52.数据库约束:
数据库的五种约束:NOT NULL,UNIQUE,PRIMARY KEY,FOREIGN KEY,CHECK
唯一约束 唯一约束UNIQUE不可以出现重复值,但是可以出现多个null值,因为在数据库中null不等于null, 单个字段直接在后面加unique
给多个列建立约束
两列组合建立约束,两列值得组合不能重复
主键约束 主键约束相当于非空约束和唯一约束(既不允许出现重复值也不可以出现null值) 创建主键约束:(列级别,和表级别)
主键自增长(mysql可以,oracle不可以如此设置)
外键约束 外键约束一对一 一对多 多对多
check约束 mysql的check约束是没作用的
索引 索引是放在模式shcema中的一个对象,必须属于某个表,在数据字典中独立存放。 创建和删除索引:
视图 视图介绍(就是一个查询结果及集):
创建和删除视图: 还有就是视图其实就是一条命名的SQL语句,一般仅仅作为查询使用,所以mysql会在创建视图时候用with check option来限定,oracle用with read only来限定
53.DML(数据操作)语句(插入insert into,修改update,删除delete): insert into:
update:
delete:
SQL语句 54.单表查询: select语句可以使用运算符(在字段 和where条件)、 Mysql字符串连接要注意null值得特殊地方,不能像java里面那样用+ 来拼接,要用conncat函数来拼接,对mysql而言,如果算术表达式使用null将使得整个算术表达式返回值为Null,如果字符串连接运算中出现null,将会导致连接后的结果也是Null.
列(字段)和表都是可以起别名的,这个是基础常识 distinct关键字去除重复值,如果紧跟在select后那么就是去除后面若干字段组合的重复著
sql中的比较运算符也可以比较字符串,日期之间的大小
注意like关键字用于模糊查询的写法_ 下划线匹配任意一个字符,% 匹配多个字符 like '孙%';------>就是查找姓 孙 的同学 like '__';------>就是查查找名字为两个字的同学 (两个下划线_ 在这里显示效果连一起了)
如果查询条件有_或者%(下划线或者百分号),mysql可以用\反斜杠转义,标准sql用escape
在sql语句中判断某些值不为空要用 is not null 不能用=null,因为SQL中null=null返回null
order by要注意多列排序的情况
55.数据库函数:(不推荐使用) mysql关于null的函数
组函数,avg count max min sum 注意以上五个函数里面distinct的使用,count是计算总条数目。使用count计算行数目时,null不会计算在内。
group by-------having
56.子查询:在查询语句中嵌套另一个查询 情况一:子查询在from后就是一个数据表(在此叫做行内视图)
情况二:子查询在where后,相当于一个条件,但是分为一个值和多个值的情况。 1.子查询返回值单行,单列值(说白了就是一个值),当成标量值使用 ,> < = 不等于判断条件
2.子查询返回多个值,可以用in any all 结合比较运算符来判定
57.集合运算:交集 并集 差集 union:条件:一,两个结果集所包含的数据列的个数一致、二,两个结果及所包含的数据列的数据类型也必须一一对应
minus:(差集)mysql并不支持
intersect:(交集) mysql不支持
JDBC 58.熟悉几个概念DriverManager Connection Statement PrepareStatement (通常是带参数的SQL语句,还可以防止SQL注入) ResultSet
statement常用的3个方法:update会返回受影响的记录数(几条)
JDBC编程步骤: 1.加载驱动(不同数据库写法不一样)
2. 创建连接 3. 创建Statement对象 4.使用Statement执行查询 5.处理结果集合 6.回收资源(关闭连接等)
59.PreparementStatement的好处(预编译、防止SQL注入,无需要拼接SQL语句)