`
tzq668766
  • 浏览: 81585 次
  • 性别: Icon_minigender_1
  • 来自: 沈阳
社区版块
存档分类
最新评论

CoreJava学习心得16

阅读更多
Java5.0的新特性

自动装箱和自动拆箱

自动封箱和自动拆箱,它实现了简单类型和封装类型的相互转化时,实现了自动转化。

自动封箱解箱只在必要的时候才进行。还有其它选择就用其它的
byte b     -128~127
Byte b     多一个null

简单类型和封装类型之间的差别
封装类可以等于null  ,避免数字得0时的二义性。
Integer i=null;
int ii=i;  (会抛出NullException 异常)
相当于 int ii=i.intValue();
Integer i=1;相当于Integer i=new Integer(1);

在基本数据类型和封装类之间的自动转换
5.0之前
Integer i=new Integer(4);
int  ii= i.intValue();

5.0之后
Integer i=4;
Long l=4.3;

静态引入

静态成员的使用,使用import static 引入静态成员,也就是可以用静态引入是导入包中的某个类的静态成员,在使用时不用再写类名。
很简单的东西,看一个例子:

没有写静态引入

public class Test{
public static void main(String[] args){
Math.sqrt(Math.pow(x, 2) + Math.pow(y, 2));
}
}

写了静态引入
import static java.lang.Math.*;
public class Test{
public static void main(String[] args){
System.out.println(sqrt(pow(x, 2) + pow(y, 2)));
}
}

其中import static java.lang.Math.*;就是静态导入的语法,它的意思是导入Math类中的所有static方法和属性。这样我们在使用这些方法和属性时就不必写类名。

需要注意的是默认包无法用静态导入,另外如果导入的类中有重复的方法和属性则需要写出类名,否则编译时无法通过。

增强的for循环

for-each循环实现了对数组和集合的便利的统一,解决遍历数组和遍历集合的不统一。

import java.util.*;
import java.util.Collection;

public class Foreach
{
private Collection<String> c = null;
    private String[] belle = new String[4];
    public Foreach()
    {
      	belle[0] = "西施";
        	belle[1] = "王昭君";
        	belle[2] = "貂禅";
        	belle[3] = "杨贵妃";
        	c = Arrays.asList(belle);
    }
    public void testCollection(){
        for (String b : c){
              System.out.println("曾经的风化绝代:" + b);
        }
    }
    public void testArray(){
        for (String b : belle){
              System.out.println("曾经的青史留名:" + b);
        }
    }
    public static void main(String[] args){
        Foreach each = new Foreach();
        each.testCollection();
        each.testArray();
    }
}
 


对于集合类型和数组类型的,我们都可以通过foreach语法来访问它。上面的例子中,以前我们要依次访问数组,挺麻烦:

for (int i = 0; i < belle.length; i++){
        String b = belle[i];
        System.out.println("曾经的风化绝代:" + b);
}


现在只需下面简单的语句即可:

for (String b : belle){
       System.out.println("曾经的青史留名:" + b);
}

对集合的访问效果更明显。以前我们访问集合的代码:
for (Iterator it = c.iterator(); it.hasNext();){
        String name = (String) it.next();
        System.out.println("曾经的风化绝代:" + name);
}

现在我们只需下面的语句:
for (String b : c){
        System.out.println("曾经的风化绝代:" + b);
}
 
Foreach也不是万能的,它也有以下的缺点:

在以前的代码中,我们可以通过Iterator执行remove操作。

for (Iterator it = c.iterator(); it.hasNext();){
       it.remove();
}

但是,在现在的for-each版中,我们无法删除集合包含的对象。你也不能替换对象。

同时,你也不能并行的for-each多个集合。所以,在我们编写代码时,还得看情况而使用它。



可变长的参数
在java5.0中,可以使用一种变长参数,也就是例如m(String… s)的东西,编译器会自动的将方法调用时的参数适当的封装成数组
5.0之前
public class Test{
public static void main(String[] args){
}
}
JVM收到数据封装在数组里,然后传入方法
5.0之后
public class Test{
public static void main(String... s){
	m();//此时实际调用的是那个无参的m()方法
//注意:调用可变长参数的方法,只在必要时调用
		m(1,“abc”,”bcd”);
}
public static void m(){
	System.out.println(“m()”);
}
public static void m(int a,String… s){
for(String s2:s){
			System.out.println(s2+a);
}
} 
}


注意:只在必要的时候进行。同时有参数为数组,就不能使用变长参数,有变长参数,就不能使用数组,不能共存。一个方法最多只能有一个变长参数,而且是最后一个参数。


格式化输出

格式化I/O(Formatted I/O)

java.util.Sacner类可以进行格式化的输入,可以使用控制台输入,结合了BufferedReader和StringTokenizer的功能。

增加了类似C的格式化输入输出,简单的例子:

public class TestFormat{
  public static void main(String[] args){
    	int a = 150000, b = 10;
    	float c = 5.0101f, d = 3.14f;
    	System.out.printf("%4d %4d%n", a, b);
    	System.out.printf("%x %x%n", a, b);
    	System.out.printf("%3.2f %1.1f%n", c, d);
    	System.out.printf("%1.3e %1.3e%n", c, d*100);
  	}

}

输出结果为:

150000   10

249f0 a

5.01 3.1

5.010e+00 3.140e+02


类型安全的枚举

枚举也是一个类型,枚举中的对象只能定义一次并在定义时给其初始化,定义之后不能再改变其值,只能从枚举中选择其一。

enum 枚举名{
枚举值1(..),枚举值2(..),.....;
}

在5.0之前使用模式做出枚举
final class Season{
public static final Season SPRING=new Season();
public static final Season WINTER=new Season();
public static final Season SUMMER=new Season();
public static final Season AUTUMN=new Season();
private Season(){}
}
完全等价于
enum Season2{
SPRING(..),//枚举值
SUMMER(..),
AUTUMN(..),
WINTER(..);
......
}

枚举是一个反射关联的典型,反射关联,即在类的定义中有自身类型的属性。
枚举本质上也是一个类,Enum是枚举的父类。
枚举中的values()方法会返回枚举中的所有枚举值
枚举中可以定义方法和属性,最后的一个枚举值要以分号和类定义分开,枚举中可以定义的构造方法。
枚举可以实现接口,枚举不能有子类也就是final的,枚举的构造方法是private(私有的),枚举中可以定义抽象方法,可以在枚举值的值中实现抽象方法,枚举值就是枚举的对象,枚举默认是final,枚举值可以隐含的匿名内部类来实现枚举中定义抽象方法。

枚举类(Enumeration Classes)和类一样,具有类所有特性。Season2的父类是java.lang.Enum;

隐含方法Season2[] ss=Season2.values();  每个枚举类型都有的方法。enum可以在switch,case语法中使用(不加类名)。
例:
switch( s ){
case SPRING:
…………….
case SUMMER:
…………….
…………..
}

枚举类可以写有参构造方法,注意这个构造方法的权限修饰符要是private即私有的,且枚举类的构造方法默认权限修饰符不是default而是private
enum Season2{
	SPRING(“春”),
	SUMMER(“夏”),
	AUTUMN(“秋”),
	WINTER(“冬”);//注意这个分号,它代表枚举值结束
	private String name;
	Season2(String name){
		this.name=name;
}
String getName(){
	return name;
}

}
Season2.SPRING.getName();


枚举的高级用法:

枚举类中可以定义抽象方法,虽然枚举类是不能有子类的但是,枚举值可以覆盖枚举类中的定义的抽象方法。
例如下:
enum Operation{
	ADD{//可以在枚举之中覆盖抽象方法
		public double calculate(double s1,double s2){
			return s1+s2;
		}
	},
	SUBSTRACT{
		public double calculate(double s1,double s2){
			return s1-s2;
		}
	},
	MULTIPLY{
		public double calculate(double s1,double s2){
			return s1*s2;
		}
	},
	DIVIDE{
		public double calculate(double s1,double s2){
			return s1/s2;
		}
	};
	public abstract double calculate(double s1 ,double s2);//抽象方法
}

有抽象方法枚举元素必须实现该方法。

java5.0中的泛型

说明

增强了java的类型安全,可以在编译期间对容器内的对象进行类型检查,在运行期不必进行类型的转换。而在java se5.0之前必须在运行期动态进行容器内对象的检查及转换,泛型是编译时概念,运行时没有泛型

减少含糊的容器,可以定义什么类型的数据放入容器


  List<Integer> aList = new ArrayList<Integer>();

    aList.add(new Integer(1));

    // ...

    Integer myInteger = aList.get(0);
支持泛型的集合,只能存放制定的类型,或者是指定类型的子类型。

我们可以看到,在这个简单的例子中,我们在定义aList的时候指明了它是一个只接受Integer类型的ArrayList,当我们调用aList.get(0)时,我们已经不再需要先显式的将结果转换成Integer,然后再赋值给myInteger了。而这一步在早先的Java版本中是必须的。也许你在想,在使用Collection时节约一些类型转换就是Java泛型的全部吗?远不止。单就这个例子而言,泛型至少还有一个更大的好处,那就是使用了泛型的容器类变得更加健壮:早先,Collection接口的get()和Iterator接口的next()方法都只能返回Object类型的结果,我们可以把这个结果强制转换成任何Object的子类,而不会有任何编译期的错误,但这显然很可能带来严重的运行期错误,因为在代码中确定从某个Collection中取出的是什么类型的对象完全是调用者自己说了算,而调用者也许并不清楚放进Collection的对象具体是什么类的;就算知道放进去的对象“应该”是什么类,也不能保证放到Collection的对象就一定是那个类的实例。现在有了泛型,只要我们定义的时候指明该Collection接受哪种类型的对象,编译器可以帮我们避免类似的问题溜到产品中。我们在实际工作中其实已经看到了太多的ClassCastException。

用法

声明及实例化泛型类:

HashMap<String,Float> hm = new HashMap<String,Float>();
编译类型的泛型和运行时类型的泛型一定要一致。没有多态。
不能使用原始类型

GenList<int> nList = new GenList<int>(); //编译错误

Java SE 5.0目前不支持原始类型作为类型参数(type parameter)

定义泛型接口:

public interface GenInterface<T> {
  void func(T t);
}

定义泛型类:

public class ArrayList<ItemType> { ... }

public class GenMap<T, V> { ... }

例1:

public class MyList<Element> extends LinkedList<Element>
{
    public void swap(int i, int j){
        Element temp = this.get(i);
        this.set(i, this.get(j));
        this.set(j, temp);
    }

    public static void main(String[] args){
        MyList<String> list = new MyList<String>();
        list.add("hi");
        list.add("andy");
        System.out.println(list.get(0) + " " + list.get(1));
        list.swap(0,1);
        System.out.println(list.get(0) + " " + list.get(1));
    }

}


泛型的通配符"?"

? 是可以用任意类型替代。
<?>泛型通配符表示任意类型
<? extends 类型>表示这个类型是某个类型的子类型,或是某个接口的实现类
<? super 类型>表示这个类型是某个类型的父类型。
例:泛型通配符、带范围的泛型通配符
import java.util.*;
import static java.lang.System.*;
public class TestTemplate {

	/**
	 * @param args
	 */
	public static void main(String[] args) {
		List<String> l1=new ArrayList<String>();
		l1.add("abc");
		l1.add("def");
		List<Number> l2=new ArrayList<Number>();
		l2.add(1.3);
		l2.add(11);
		List<Integer> l3=new ArrayList<Integer>();
		l3.add(123);
		l3.add(456);
		
	//	print(l1);
		print(l2);
		print(l3);
	}

	static void print(List<?> l//泛型通配符){
//所有Comparable接口的实现类可以作为泛型参数
		for(Object o:l){
			out.println(o);
		}
	}

	static void print(List<? extends Number> l//带范围的泛型通配符){
//所有Number的子类可以作为泛型参数
		for(Object o:l){
			out.println(o);
		}
	}
	static void print(List<? extends Comparable> l){
//所有Comparable接口的实现类可以作为泛型参数
		for(Object o:l){
			out.println(o);
		}
	}

static void print(List<? super Number> l){
//所有Number的父类可以作为泛型参数
		for(Object o:l){
			out.println(o);
		}
	}

}

"?"可以用来代替任何类型, 例如使用通配符来实现print方法。

public static void print(GenList<?> list) {})

泛型方法的定义

把数组拷贝到集合时,数组的类型一定要和集合的泛型相同。
<...>定义泛型,其中的"..."一般用大写字母来代替,也就是泛型的命名,其实,在运行时会根据实际类型替换掉那个泛型。

需要泛型参数或返回值同时又是某个类的子类又是某个接口的实现类的时候,可以使用
<? extends Xxxx & Xxxx>这种写法,注意:接口类型要放在类的后面,且只能使用’&’符。

例:

public class Test{
<E> void copyArrayToList(E[] os,List<E> lst){
		for(E o:os){
			lst.add(o);
			}
	}

static <E extends Number> void copyArrayToList(E[] os,List<E> lst){
			for(E o:os){
			lst.add(o);
			}
		}

static<E extends Number & Comparable> void copyArrayToList(E[] os,List<E> lst){
		for(E o:os){
			lst.add(o);
		}
	}
}

受限泛型是指类型参数的取值范围是受到限制的。
extends关键字不仅仅可以用来声明类的继承关系, 也可以用来声明类型参数(type parameter)的受限关系。例如, 我们只需要一个存放数字的列表, 包括整数(Long, Integer, Short), 实数(Double, Float), 不能用来存放其他类型, 例如字符串(String), 也就是说, 要把类型参数T的取值泛型限制在Number极其子类中.在这种情况下, 我们就可以使用extends关键字把类型参数(type parameter)限制为数字
只能使用extends不能使用 super,只能向下,不能向上。
注意:只有参数表中可以使用<?> ,定义泛型时用 <E>

泛型类的定义

我们也可以在定义类型中使用泛型
注意:静态方法中不能使用类的泛型,因为泛型类是在创建对象的时候给定泛型。
例:
class MyClass<E>{
	public void show(E a){
		System.out.println(a);
	}
	public E get(){
		return null;
	}
	
}


受限泛型

class MyClass <E extends Number>{
	public void show(E a){

	}
}


泛型与异常

泛型参数在catch块中不允许出现,但是能用在方法的throws之后。例:

import java.io.*;

interface Executor<E extends Exception> {
    void execute() throws E;
}

public class GenericExceptionTest {
    public static void main(String args[]) {
        try {
              Executor<IOException> e = new Executor<IOException>() {
                  public void execute() throws IOException{
                      // code here that may throw an
                      // IOException or a subtype of
                      // IOException
                  }
                 };
              e.execute();
        } catch(IOException ioe) {
              System.out.println("IOException: " + ioe);
              ioe.printStackTrace();
        }
    }
}



泛型的一些局限型

catch不能使用泛型,在泛型集合中,不能用泛型创建对象,不允许使用泛型的对象。

不能实例化泛型

T t = new T(); //error

不能实例化泛型类型的数组

T[] ts= new T[10];   //编译错误

不能实例化泛型参数数

Pair<String>[] table = new Pair<String>(10); // ERROR

类的静态变量不能声明为类型参数类型

public class GenClass<T> {
  private static T t;   //编译错误
}
静态方法可以是泛型方法,但是不可以使用类的泛型。

泛型类不能继承自Throwable以及其子类

public GenExpection<T> extends Exception{}   //编译错误

不能用于基础类型int等

Pair<double> //error

Pair<Double> //right
分享到:
评论

相关推荐

    Core Java 学习笔记

    《Core Java》学习笔记。 我把自己的笔记都以注释的形式写在代码里面了,这样方便理解。 尽管有些部分被标记为“已完成”,但实际上以后说不定我还会折返回来进行修改或者添加一些注释。 当然如果你有什么不理解...

    CoreJava卷一学习笔记

    自己学习corejava核心技术卷一时的学习笔记和心得,提出的一些问题

    corejava练习题目(1)

    综上所述,"CoreJava练习题目(1)"是一个非常实用的Java学习资源。它通过一系列贴近实际应用的编程习题,帮助学习者将理论知识转化为实践技能,提升自身的编程能力。无论是编程初学者还是希望进一步提升技术的开发者...

    Java学习笔记及心得

    ### Java学习笔记及心得知识点详细解析 #### 标题:Java学习笔记及心得 #### 描述:Core Java 学习笔记及心得 pdf格式可打开。涵盖了java的基础入门知识,非常适合自学的及想深入学习理解的同学。 #### 标签:...

    Core Java心得笔记

    【Core Java心得笔记】主要涵盖了Java编程的基础及进阶知识,包括对象导向编程、类与对象、封装、继承、多态、接口、异常处理、集合框架、IO流、线程等核心概念。以下是对这些知识点的详细阐述: 1. **对象导向编程...

    Corejava 核心java笔记

    这份名为"Corejava 核心java笔记"的资料应该包含了作者在学习Java基础时的一些理解和实践心得,对于初学者来说是一份宝贵的参考资料。 1. **Java语法**: Java语法简洁而严谨,包括变量声明、数据类型(如整型、浮点...

    UNIX、Oracle、CoreJava语言基础实训心得.pdf

    "UNIX、Oracle、CoreJava语言基础实训心得.pdf" 本文档主要介绍了UNIX、Oracle和Core Java语言基础实训的知识点,涵盖了宽带运营支撑系统、UNIX基本命令、Oracle数据库SQL命令、Java语言的基本概念等方面。 一、...

    UNIX、Oracle、CoreJava语言基础实训心得.docx

    在本次的实训中,主要涉及了三个核心领域:UNIX操作系统、Oracle数据库管理和Core Java编程语言。以下是关于这些领域的详细知识: 1. **UNIX操作系统**: - **WOSS系统**:Wide-Brand Operation Support System是...

    UNIX、Oracle、Core Java 语言基础实训心得.doc

    在本次“UNIX、Oracle、Core Java 语言基础实训”中,我深入学习了这三个关键领域的基础知识,并且在实践中积累了丰富的经验。UNIX系统是广泛应用于服务器环境的操作系统,其稳定性和高效性是其核心优势。在实训过程...

    C# 学习心得(最新)

    作为.NET框架的重要组成部分,C#结合了C++的强类型系统和Java的简洁性,提供了一种高效、安全且现代的编程环境。 在学习C#的过程中,有几个核心知识点是必不可少的: 1. **基础语法**:C#的基础语法包括变量声明、...

    C# 自学学习心得

    本文将基于"C#自学学习心得"的标题和描述,详细探讨C#中的WinForm和WebForm开发,以及相关的学习经验。 首先,让我们从C#的基础开始。C#是由微软公司开发的一种面向对象的语言,它具有简洁、类型安全和性能高效的...

    Spring学习心得(一)

    在Spring框架的学习过程中,我们可以深入理解到它在Java企业级应用中的核心作用。Spring作为一个开源的、全面的企业级应用开发框架,它简化了Java EE(Enterprise Edition)开发,提供了丰富的功能,包括依赖注入...

    [计算机]JAVA入门书籍读后感.doc

    【描述】:这份读后感来源于一篇《电子商务基础》课程的大作业,作者蒋凤娇在指导教师张文胜的指导下,于2011年6月完成了对JAVA入门书籍《Core Java》的学习心得。 【标签】:“文档资料” 【正文】: 《Core ...

    java笔记图解11

    总的来说,这份"Java笔记图解11"资料涵盖了从基础到进阶的Java编程知识,从集合框架到框架使用,再到Map接口的深入学习,以及个人学习心得和核心技术的详细研究。通过这些内容的学习,可以系统提升Java编程技能,为...

    java核心技术

    Cay S.Horstmann等编著,公飞编译的《Java核心技术》(Core Java), 自第1版出版以来,一直备受广大Java程序设计人员的青睐,畅销不衰,是, Java经典书籍。第8版针对Java SE 6平台进行了全面更新,囊括了Java平, 台...

    Spring学习心得(二)——日志和数据库

    在本文中,我们将深入探讨这两个关键领域,并基于给出的"Spring学习心得(二)——日志和数据库"这个标题进行详细的阐述。 首先,让我们从日志开始。在Java应用程序中,日志系统扮演着调试、监控和问题排查的关键角色...

    Java 推荐读物与源代码阅读

    因此,在入门阶段可以选择Prentice Hall PTR的《Core Java 2》(国内称为《Java 2核心技术》),这本书更为适合初学者,目前已经有第七版,可以在网上找到电子版资源。另一本不错的选择是O'Reilly出版社的《Java in ...

Global site tag (gtag.js) - Google Analytics