java.util的最初版本中不包括类集框架。 取而代之,它定义了几个类和接口提供专门的方法用于存储对象。
随着在Java 2中引入类集,有几种最初的类被重新设计成支持类集接口,因此它们与框架完全兼容。尽管实际上没有类被摈弃,但其中某些方法仍被认为是过时的。当然,在那些重复从以前版本遗留下来的类的功能性的地方,通常都愿意用类集编写新的代码程序。
一般来说,对从以前版本遗留下来的类的支持是因为仍然存在着大量使用它们的基本代码,包括现在仍在被Java 2的应用编程接口(API)使用的程序。
另一点,没有一个类集类是同步的。但是所有的从以前版本遗留下来的类都是同步的。 这一区别在有些情况下是很重要的。当然,通过使用由Collections提供的算法也很容易实现类集同步。
由java.util定义的从以前版本遗留下来的类如下:Dictionary、Hashtable、Properties、Stack和Vector。
下面将介绍部分从以前版本遗留下来的类:
一、Stack类
Stack是Vector的一个子类,它实现标准的后进先出堆栈。Stack仅仅定义了创建空堆栈的默认构造方法。Stack包括了由Vector定义的所有方法,同时增加了几种它自己定义的方法,具体总结在下表中:
方法 | 描述 |
---|---|
boolean empty() | 如果堆栈是空的,则返回true;反之,返回false |
Object peek() | 返回位于栈顶的元素,但是并不在堆栈中删除它 |
Object pop() | 返回位于栈顶的元素,并在堆栈中删除它 |
Object push(Object element) | 将element压入堆栈,同时也返回element |
int search(Object element) | 在堆栈中搜索element,如果发现了,则返回它相对于栈顶的偏移量 |
下面看个例子,将几个整型(Integer)压入堆栈,然后再将它们弹出:
package com.xy.test2;
import java.util.EmptyStackException;
import java.util.Stack;
public class StackDemo1 {
static void showPush(Stack<Integer> st, int a) {
st.push(new Integer(a));
System.out.println("-->入栈(" + a + ")");
System.out.println("Stack:" + st);
}
static void showPop(Stack<Integer> st) {
System.out.println("出栈-->");
Integer a = (Integer)st.pop();
System.out.println(a);
System.out.println("Stack:" + st);
}
public static void main(String[] args) {
Stack<Integer> st = new Stack<Integer>();
System.out.println("Stack:" + st);
showPush(st, 42);
showPush(st, 66);
showPush(st, 47);
showPop(st);
showPop(st);
showPop(st);
// 出栈时会有一个EmptyStackException的异常,需要进行异常处理
try {
showPop(st);
}
catch(EmptyStackException e) {
System.out.println("出栈异常: 栈中内容为空");
e.printStackTrace();
}
}
}
【结果】
二、Dictionary类
字典(Dictionary)是一个表示关键字/值存储库的抽象类,同时它的操作也很像映射(Map)。给定一个关键字和值,可以将值存储到字典(Dictionary)对象中。一旦这个值被存储了,就能够用它的关键字来检索它。因此与映射一样,字典可以被当做关键字/值对列表来考虑。
尽管在Java 2中并没有摈弃字典(Dictionary),但由于它已经被映射(Map)所取代,从而被认为是过时的。然而目前Dictionary仍然被广泛地使用,因此这里仍对它进行简要的讨论。
由Dictionary定义的抽象方法如下表所示:
方法 | 描述 |
---|---|
Enumeration elements() | 返回对包含在字典中的值的枚举 |
Object get(Object key) | 返回一个包含与key相连的值的对象。如果key不在字典中,则返回一个空对象 |
boolean isEmpty() | 如果字典为空,返回true;反之,返回false |
Enumeration keys() | 返回包含在字典中的关键字的枚举 |
Object put(Object key, Object value) | 将一个关键字和它的值插入字典中。如果key不在字典中,则返回null;如果key已经在字典中了,则修改value,然后返回与key相关联的前一个值。 |
Object remove(Object key) | 删除key和它的值,返回与key相关联的值。如果key不在字典中,则返回null。 |
int size() | 返回字典中的项数,使用put()方法在字典中增加关键字和值。使用get()方法检索给定关键字的值。当分别使用keys()和elements()方法进行枚举时,关键字和值可以分别逐个地返回。 |
Dictionary类是过时的。推荐读者使用Map接口去获得关键字/值存储的功能。
三、属性操作类——Properties类
属性(Properties)是Hashtable的一个子类。但是属性(Properties)与Hashtable最大的不同在于:它所能够操作的数据全部是String,Key和Value的类型全部都是字符串。
Properties类被许多其他的Java类所使用。例如,当获得系统环境值时,System.getProperties( )返回对象的类型。
Properties定义了下面的实例变量。
Properties defaults;
这个变量包含了一个与属性(Properties)对象相关联的默认属性列表。
Properties定义了如下的构造方法:
(1)Properties( ) :创建一个没有默认值的属性(Properties)对象。
(2)Properties(Properties propDefault) :创建一个将propDefault作为其默认值的对象。
在这两种情况下,属性列表都是空的。
除了Properties从Hashtable中继承下来的方法之外,Properties自己定义的方法列在下表中。Properties也包含了一个不被赞成使用的方法。save()。它被store()方法所取代,因为它不能正确地处理错误。
Properties类的一个有用功能是可以指定一个默认属性,如果没有值与特定的关键字相关联,则返回这个默认属性。
例如,默认值可以与关键字一起在getProperty( )方法中被指定—如getProperty(“name”,“default value”)。
如果“name”值没有找到,则返回“defaultvalue”。当构造一个Properties对象时,可以传递Properties的另一个实例作为新实例的默认值。在这种情况下,如果对一个给定的Properties对象调用getProperty(“foo”),而“foo”并不存在时,Java在默认Properties对象中寻找“foo”。它允许默认属性的任意层嵌套。
下面的例子说明了Properties的使用。该程序创建一个属性列表,在其中关键字是各国的名称,值是这些国家的首都。注意试图寻找包括默认值的美国首都时的情况:
package com.xy.test2;
import java.util.Iterator;
import java.util.Properties;
import java.util.Set;
public class PropertiesDemo {
public static void main(String[] args){
Properties capitals = new Properties();
String str;
capitals.put("中国","北京");
capitals.put("俄罗斯","莫斯科");
capitals.put("日本","东京");
capitals.put("法国","巴黎");
capitals.put("英国","伦敦");
//返回包含映射中项的集合
Set<Object> states = capitals.keySet();
Iterator<Object> itr=states.iterator();
while(itr.hasNext()){
str=(String)itr.next();
System.out.println("国家:"+str+",首都:"+capitals.getProperty(str)+".");
}
System.out.println();
//查找列表,如果没有则显示为“没发现”
str=capitals.getProperty("美国","没有发现");
System.out.println("美国的首都:"+str+".");
}
}
【结果】
在Properties类中使用store()和load()方法
Properties类的一个最有用的方面是可以利用store()和load()方法方便地对包含在属性(Properties)对象中的信息进行存储或从盘中装入信息。在任何时候,都可以将一个属性(Properties)对象写入流或从中将其读出。这使得属性列表特别便于实现简单的数据库。
package com.xy.test2;
import java.io.*;
import java.util.*;
public class PropertiesDemo1 {
public static void main(String[] args) {
Properties settings = new Properties();
try {
settings.load(new FileInputStream("d:\\count.txt"));
}
catch(Exception e) {
settings.setProperty("count", new Integer(0).toString());
}
int c = Integer.parseInt(settings.getProperty("count"))+1;
System.out.println("这是本程序第" + c + "次被使用");
settings.put("count", new Integer(c).toString());
try {
settings.store(new FileOutputStream("d:\\count.txt"),
"PropertiesFile use it.");
}
catch(Exception e) {
System.out.println(e.getMessage());
}
}
}
【结果】
程序每次启动时都去读取那个记录文件,直接取出文件中所记录的运行次数并加1后,又重新将新的运行次数存回文件。由于第1次运行时硬盘上还没有那个记录文件,程序去读取那个记录文件时会报出一个异常,就在处理异常的语句中将属性的值设置为0,表示程序以前还没有被运行过。如果要用到Properties类的store()方法进行存储,每个属性的关键字和值都必须是字符串类型的,所以上面的程序没有用从父类HashTable继承到的put、get方法进行属性的设置与读取,而是直接用了Properties类的setProperty()、getProperty()方法进行属性的设置与读取。