处理基本数据类型 Buffer 内幕 内存映像文件 性能 文件锁闭 压缩 生成 GZIP 压缩文件 对象串行化 恢复对象 正则表达式 生成正则表达式... 41

Size: px
Start display at page:

Download "处理基本数据类型 Buffer 内幕 内存映像文件 性能 文件锁闭 压缩 生成 GZIP 压缩文件 对象串行化 恢复对象 正则表达式 生成正则表达式... 41"

Transcription

1 第十三讲 Java I/O 系统 他应该瞪大眼睛盯着诺亚, 好好学习一下, 看他们是怎样把那么多东西装到一个小小的方舟上的 西德尼 十三 Java I/O 系统 第十三讲 Java I/O 系统 类 File... 3 列出文件夹的文件清单... 3 检查文件夹, 生成文件夹 输入输出... 6 InputStream 的类别...6 OutputStream 的类别 增加有用的属性和接口... 9 FilterInputStream 过滤输入流 FilterOutputStream 过滤输出流 Reader 及 Writer 数据源和数据汇点 改变数据流的行为 没有改变的类 RandomAccessFile I/O 流的使用方法 输入流 输出流 管道流 标准 I/O 从标准输入读入 将 System.out 转换为 PrintWriter...23 标准 I/O 重定向 新 I/O 数据转换 (1/52)

2 处理基本数据类型 Buffer 内幕 内存映像文件 性能 文件锁闭 压缩 生成 GZIP 压缩文件 对象串行化 恢复对象 正则表达式 生成正则表达式 Pattern 和 Matcher...45 find() Pattern 标志选项 split()...47 替换操作 正规表达式与 JavaI/O StringTokenizer 还有用吗? (2/52)

3 设计一个良好的输入 / 输出系统是语言设计人员的最难的工作之一 最大的挑战在于必须考虑各种可性能 输入输出不仅有多种数据源和数据汇点, 而且还要考虑与这些数据源 数据汇点的各种交流方式 ( 比如顺序访问 随机访问 缓存方式 二进制 字符形式 按行存取, 按单词存取等等 ) Java 类库设计人员通过很多类来完成这些功能, 实际上 JavaI/O 类库的类多得让人有些眼花 JavaI/O 类库在 Java1.0 之后也有很多改进, 在 Java1.2.0 中, 在原先面向字节的类库的基础上, 增加面向字符, 以 Unicode 为基础的 I/O 类库 而在 Java1.4 又新增了 nio 类库, 主要目的是改进 I/O 类库的性能和功能 由此, 在真正了解 JavaI/O 全貌, 能够利用类库之前, 我们必须掌握若干类的用法 同时, 了解 JavaI/O 的进化过程, 对于真正地理解 JavaI/O 类库也至关重要 1. 类 File 类 File 有一个令人迷惑的名称 我们首次看到它, 以为与文件相关, 实际上不是 : 它代表一个文件的名称或某个文件夹中一组文件的名称 当它代表一组文件时, 我们通过其 list() 方法, 获得该组文件的清单 列出文件夹的文件清单 当 File 对象指向一个文件夹时, 我们可以用两种方式列出其中的文件清单 当调用 list() 方法 而不给它任何参数时, 我们获得该文件夹中所有文件的清单 如果只想列出其中一部分文件, 比如只列出扩展名为.java 的文件, 我们就使用一个 FilenameFilter 对象来过滤这个清单 // Lec13: DirList.java import java.io.*; import java.util.*; import java.util.regex.*; public class DirList { public static void main(final String[] args){ File path = new File("."); String[] list; if(args.length == 0) list = path.list(); else 13-(3/52)

4 list = path.list(new FilenameFilter(){ private Pattern pattern = Pattern.compile(args[0]); public boolean accept(file dir, String name){ return pattern.matcher( new File(name).getName() ).matches(); ); Arrays.sort(list, new Comparator(){ public int compare(object o1, Object o2){ String s1 = (String)o1, s2 = (String)o2; return s1.tolowercase().compareto(s2.tolowercase()); ); for(int i=0; i<list.length; i++) System.out.println(list[i]); FilenameFilter 是一个非常简单的接口 : public interface FilenameFilter { boolean accept(file dir, String name); 其主要功能是定义 accept() 方法 方法 list() 通过回叫 accept() 来决定哪个文件名称应被包含在清单中 accept() 方法接受两个参数, 第一个参数是 File 对象, 表示文件所在的文件夹, 第二个参数是一个 String 对象, 表示文件的名称 DirList 中,accept() 方法利用一个正规表达式 Matcher 对象来判断这个正规表达式是否与文件名称相匹配 File.getName() 返回的是去掉路径名称之后的文件名 检查文件夹, 生成文件夹 我们也可以利用 File 对象生成一个新的文件夹或整个文件夹路径 我们也可以查阅文件的属 性 ( 如大小, 最后修改时间, 读写性等 ) 也可以判断一个 File 对象代表一个文件还是文件 夹 我们还可以用一个 File 对象删除一个文件 // Lec13: MakeDirectories.java import java.io.*; import java.util.*; public class MakeDirectories { private static void usage(){ 13-(4/52)

5 System.out.println( "Usage: MakeDirectories path1...\n" + "Creates each path.\n" + "Usage: MakeDirectories -d path1...\n" + "Deletes each path.\n" + "Usage: MakeDirectories -r path1 path2\n" + "Renames from path1 to path2."); System.exit(1); private static void filedata(file f){ System.out.println( "Absolute Path: " + f.getabsolutepath() + "\n Can Read: " + f.canread() + "\n Can write: " + f.canwrite() + "\n getname: " + f.getname() + "\n getparent: " + f.getparent() + "\n getpath: " + f.getpath() + "\n length: " + f.length() + "\n lastmodified: " + new Date(f.lastModified())); public static void main(string[] args){ if(args.length < 1) usage(); if(args[0].equals("-r")){ if(args.length!= 3) usage(); File old = new File(args[1]), rname = new File(args[2]); System.out.println("Renaming..." + old + " to " + rname); if(old.renameto(rname)) System.out.println("OK!"); else System.out.println("Failed!"); filedata(old); filedata(rname); return; int count = 0; boolean del = false; if(args[0].equals("-d")){ count++; del = true; count--; while(++count < args.length){ File f = new File(args[count]); if(f.exists()){ System.out.println(f + " exists"); if(del){ System.out.println("deleting..." + f ); 13-(5/52)

6 if(f.delete()) System.out.println("OK!"); else System.out.println("Failed!"); else{ // doesn't exist if(!del){ f.mkdirs(); System.out.println("created " + f); filedata(f); 程序中, 方法 filedata() 列出文件的有关属性 在 main() 方法中, 我们利用 renameto() 重新命 名文件, 利用 delete() 删除文件, 利用 mkdir() 生成文件夹 2. 输入输出 I/O 类库使用抽象概念 流, 用流表示任何可以产生或接受数据的数据源或数据汇点 流将实际 I/O 设备中的细节隐蔽了起来 JavaI/O 类库分为输入和输出两大类 : 派生自 InputStream 或 Reader 类的所有类均有 read() 方法, 它阅读一个单字节或一个字节数组 ; 派生自 OutputStream 或 Writer 类的所有类均具有 writer() 方法, 写出单个字节或一个字节数组 我们一般不直接使用这些方法, 它们存在的意义主要在于为别的更高级的类提供支持 这些更高级的类提供更有用的接口 在 Java1.0 中, 类库设计者决定所有与输入有关的类应该派生自 InputStream, 而所有与输出有关的类应该派生自 OutputStream InputStream 的类别 类 InputStream 代表各种从不同数据源产生输入的类 数据源可分为 13-(6/52)

7 1) 一个字节数组 2) 一个 String 对象 3) 一个文件 4) 一个管道 pipe 与物理管道一样, 从一端放入的事物从另一端出现 5) 一系列别的流, 组合成一个单一的流 6) 其它数据源, 如互联网连接 上述各数据源均由一个 InputStream 的子类描述 除此之外,FilterInputStream 也是一种 InputStream, 是一系列 装饰 类的基类 装饰类为 InputStream 新增一些有用的属性和接口 表 13-1 InputStream 的类别 类 ByteArrayInputStream StringBufferInputStrea m FileInputStream 功能将内存中的一块缓存作为 InputStream 使用将一个 String 对象转换为一个 InputStream 从文件阅读信息 构造方法的参数使用方法缓存, 以数组形式出现作为数据源 : 将其连接到一个 FilterInputStream 对象, 从而提供有用的接口一个 String 对象 后台使用的实际上是一个 StringBuffer 作为数据源 : 将其连接到一个 FilterInputStream 对象, 从而提供有用的接口一个代表文件名称的 String 对象, 或一个 File 对象, 或一个 FileDescripter 对象作为数据源 : 将其连接到一个 FilterInputStream 对象, 从而提供有用的接口 13-(7/52)

8 类 PipedInputStream SequenceInputStream FilterInputStream 功能与一个 PipedOutputStream 相连接 阅读写入那个 PipedOutputStream 的数据, 从而实现管道的概念 将两个或多个 InputStream 转换为一个 InputStream 是一个抽象类, 提供所有装饰类的接口, 从而为别的 InputStream 提供更有用的功能 详情况查表 13-3 构造方法的参数使用方法 PipedOutputStream 对象在多线程结构中, 作为数据源使用 将其连接到一个 FilterInputStream 对象, 从而提供更有用的接口 两个 InputStream 对象, 或一个包含了 InputStream 对象的容器的 Enumeration 对象 作为数据源 : 将其连接到一个 FilterInputStream 对象, 从而提供有用的接口查阅表 13-3 查阅表 13-3 OutputStream 的类别 表 13-2 OutputStream 的类别 类 ByteArrayOutputStream 功能在内存中生成一缓存, 写入该流的数据被存放在该缓存中 构造方法的参数用途 ( 可选 ) 缓存的初始大小指定数据的目的地 : 将其链接 - FilterOutputStream, 从而提供更有用的接口 13-(8/52)

9 类 FileOutputStream PipedOutputStream FilterOutputStream 功能将数据存入文件与一个 PipedInputStream 相连接 写入该输出流的数据将出现在对应的输入 构造方法的参数用途一个代表文件名称的 String 对象或一个 File, 或一个 FileDescriptor 对象指定数据的目的地 : 将其链接 - FilterOutputStream, 从而提供更有用的接口 PipedInputStream 对象在多线程结构中, 制定数据的目的地 将其与一个 FilterOutputStream 连接, 流, 从而实现管道的概念 从而提供更有用的接口 抽象类, 为所有输出装饰表 13-4 点提供接口, 从而为别的 OutputStream 提供更有用表 13-4 的接口 详情请查阅表 增加有用的属性和接口 利用分层对象动态地透明地为一对象增加职责的做法称为装饰模式 我们首先看看齐天大圣 的例子 13-(9/52)

10 齐天大圣是神仙类的一种, 如同 FileInputStream 或 ByteArrayInputStream 是 InputStream 的一 种 既然是神仙, 就可以变化, 但是变化后的神仙仍然是神仙 所以, 化身也是神仙的一种, 如同 FilterInputStream 也是一种 InputStream 不过无论怎样变化, 总是离不开神仙自己 所 以, 化身中也包含着神仙 孙猴有七十二变化, 可以变化为花 鸟 鱼 虫, 这些都是化身的分类 FilterInputStream 也有多种分类 孙猴可以在变成鱼之后, 再从鱼直接变成鸟, 也就是说, 装饰可以一层层叠 加上去 大圣孙悟空 = new 大圣 (); 鸟猴子变的鸟 = new 鸟 ( 孙悟空 ); 鱼猴子变的鱼 = new 鱼 ( 猴子变的鸟 ); Java 的输入流 输出流也可以层层装饰, 提供不同的 更多的功能 FilterInputStream 过滤输入流 FilterInputStream 称为过滤输入流, 它将另一个输入流作为数据源, 它与其它具体输入流的 关系, 如同 化身 与大圣的关系 表 13-3 FilterInputStream 的类别 类 DataInputStream 功能提供直接阅读基本数据类型数据 ( int,char,long 等 ) 的功能, 与 Dataoutputstream 配套使用 构造方法的参数用法 InputStream 对象阅读基本数据类型的数据, 以及 String 对象 13-(10/52)

11 类 BufferedInputStream LineNumberInputStream PushbackInputStream 功能用于缓存阅读, 从而避免每次阅读都直接从外存阅读, 改善性能 跟踪输入流中的行号 具有单个字节退回的缓存, 可以将最后一次读出的字节退回输入流 构造方法的参数用法 InputStream 以及缓存大小 ( 可选 ) 不额外增加接口, 只是增加了缓存的功能 InputStream 对象 InputStream 对象一般用于编译器程序的扫描程序, 通常不太使用 FilterOutputStream 过滤输出流 DataOutputStream 能够将基本数据类型和 String 对象写入到输出流 与 DataInputStream 配套使用 PrintStream 的主要意图是将所有基本数据类型和 String 对象以人类可见的形式打印出来 注意它与 DataOutputStream 的区别 PrintStream 将捕获所有 IOException, 所以为了检查错误情况, 我们必须调用 checkemor() 方法来查询 : 如果发生了错误, 这个方法返回 true,printstream 也不能正确地处理如汉字等语言, 这些问题在 PrintWriter 中得到了解决 13-(11/52)

12 BufferedOutputStream 不提供额外的接口, 它所完成的唯一功能是提供缓存, 从而改善硬件 的访问速度 表 13-4 FilterOutputStream 的类别 类 DataOutputStream PrintStream BufferedOutputStream 功能与 DataInputStream 配套使用完成基本数据类型的读写打印 缓存 构造方法的参数用法 Outputstream 基本数据类型和 String Outputstream 以及可选的逻辑参数, 指定每个换行缓存是否刷新 应该为装饰类的最后一层 OutputStream 以及缓存的大小 ( 可选 ) 缓存 4.Reader 及 Writer Java1.1 对基本 I/O 系统做了较大的改动, 新推出了 Reader 和 Writer 类以及其子类 装饰类 新推出的 Reader 和 Writer 类是对 InputStream 和 OutputStream 的补充 InputStream 和 OutputStream 是面向字节的, 而 Reader 和 Writer 是面向字符的, 能够处理 Unicode Java1.1 也给 InputStream 和 OutputStream 新增了子类, 也增加了适配类 InputStreamReader 和 OutputStreamWriter, 分别将 InputStream 和 OutputStream 转换为 Reader 和 Writer 推出 Reader 和 Writer 的最大的动机是支持国际化 旧的 I/O 流只支持 8 位字节, 而不能很好地支持 16 位 Unicode 字符 13-(12/52)

13 数据源和数据汇点 几乎所有的 I/O 流类都有对应的 Reader 和 Writer 但这并不意味着我们总是使用后者, 在有些地方, 面向字节的 InputStream 和 OutputStream 是正确的选择 比如,java.util.zip 类库就是面向字节的 比较合理的做法是, 首先试着使用 Reader 和 Writer, 而必需时, 使用 InputStream 和 OutputStream 下表显示了这两个系统中数据源和汇点的对应关系 表 :13-5 源和汇点 Java 1.0 Java 1.1 Reader InputStream 适配器 :InputStreamReader Writer OutputStream 适配器 :OutputStreamWriter FileInputStream FileReader FileOutputStream FileWriter StringBufferInputStream StringReader - StringWriter ByteArrayInputStream CharArrayReader ByteArrayOutputStream CharArrayWriter PipeInputStream PipedReader PipedOutputStream PipedWriter 一般来讲, 这两个系统具有相同或相似的接口 改变数据流的行为 对于 InputSream 和 OutputStream, 我们利用适当的装饰类 ( FilterInputStream 和 FilterOutputstream 的子类 ) 对他们装饰, 从而满足特殊的需求 Reader 和 Writer 类也利用同 样的概念, 但有所区别 13-(13/52)

14 下表列出了 Java1.0 装饰类与 Java1.1 装饰类之间的比较 表 :13-6 过滤类 Java 1.0 Java 1.1 FilterInputStream FilterReader FilterOutputStream FilterWriter ( 抽象类, 但是没有派生类 ) BufferedInputStream BufferedReader ( 同样提供 readline() 方法 ) BufferedOutputStream BufferedWriter PrintStream PrintWriter LineNumberInputStream (deprecated) LineNumberReader StreamTokenizer StreamTokenizer ( 使用接受 Reader 的构造方法 ) PushBackInputStream PushBackReader 主要区别在于类的组织 : 13-(14/52)

15 尽管如此,Java1.0 和 Java1.1 对应类的接口还是相当接近的 当需要用到 realine() 方法时不 应再使用 DataInputStream, 而应使用 BufferedReader, 除此之外 DataInputStream 还是 I/O 类 库的可取的一个类 13-(15/52)

16 没有改变的类 有些类从 Java1.0 升级到 Java1.1 的过程中没有改变 : DataOutputStream File RandomAccessFile SequenceInputStream 5.RandomAccessFile RandomAccessFile 用于存储已知大小的纪录的文件, 我们可以使用 seek() 方法定位一个记录, 13-(16/52)

17 然后访问它或修改它 RandomAccessFile 不是 InputStream 或 OutputStream 系统中的一员, 它与它们无关 如果说有共同点的话, 那就是 RandomAccessFile 也实现了 DataInput 和 DataOutput 接口, 而这两个接口也分别被 DataInputStream 和 DataOutputStream 实现 RandomAccessFile 的 length() 方法返回文件的最大长度, 方法 seek() 将文件指针移动到指定的位置 我们通过给 RandomAccessFile 的构造方法传递不同的参数, 决定文件是可读可写的 ( rw") 还是只读的 ( r ) 在 Java1.4 中,RandomAccessFile 的大多数功能由 nio 内存映射文件代替了 6.I/O 流的使用方法 尽管我们可以将 I/O 流的各种类以不同的方式组合起来, 但是一般情况下, 我们只是用少数 几种组合, 下面的例子可以作为参考 例中包含了各种 I/O 配置的生成和使用方法, 我们标注了编号, 对应于程序后的注解 // Lec13: IOStreamDemo.java import java.io.*; public class IOStreamDemo { public static void main(string[] args) throws IOException { // 1). 按行阅读 BufferedReader in = new BufferedReader( new FileReader("IOStreamDemo.java")); String s; StringBuffer sb = new StringBuffer(); while((s = in.readline())!= null) sb.append(s + "\n"); String s2 = sb.tostring(); // 1b). 标准输入 BufferedReader stdin = new BufferedReader( new InputStreamReader( System.in )); System.out.print("Enter a line: "); System.out.println(stdin.readLine()); 13-(17/52)

18 // 2). 从内存输入 StringReader in2 = new StringReader(s2); int c; while((c = in2.read())!= -1) System.out.print((char)c); System.out.print("Press Enter: "); stdin.readline(); // 3). 格式化内存输入 try{ DataInputStream in3 = new DataInputStream( new ByteArrayInputStream(s2.getBytes())); while(true) System.out.print((char)in3.readByte()); catch(eofexception e){ System.err.println("End of Stream"); // 4). 文件输出 try{ BufferedReader in4 = new BufferedReader( new StringReader(s2)); PrintWriter out1 = new PrintWriter( new BufferedWriter( new FileWriter("IODemo.out") ) ); int linecount = 1; while((s = in4.readline())!= null) out1.println(linecount++ + ": " + s); out1.close(); catch(eofexception e){ System.err.println("End of Stream"); // 5). 存储并恢复数据 try{ DataOutputStream out2 = new DataOutputStream( new BufferedOutputStream( new FileOutputStream( "Data.txt" ) ) ); out2.writedouble( ); out2.writeutf("this was pi"); out2.writedouble( ); out2.writeutf("square root of 2"); out2.close(); DataInputStream in5 = new DataInputStream( new BufferedInputStream( new FileInputStream( "Data.txt" ))); System.out.println(in5.readDouble()); System.out.println(in5.readUTF()); System.out.println(in5.readDouble()); 13-(18/52)

19 System.out.println(in5.readUTF()); catch(eofexception e){ throw new RuntimeException(e); // 6). 读写随机存取文件 RandomAccessFile rf = new RandomAccessFile( "rtest.dat", "rw"); for(int i = 0; i < 10; i++) rf.writedouble(i * 1.414); rf.close(); rf = new RandomAccessFile("rtest.dat", "rw"); rf.seek(5 * 8); rf.writedouble( ); rf.close(); rf = new RandomAccessFile("rtest.dat", "r"); for(int i=0; i<10; i++) System.out.println("Value " + i + ": " + rf.readdouble()); rf.close(); 输入流 程序中第 1) 至第 4) 部分演示了输入流的用法 1) 缓存输入文件为了进行字符输入, 我们使用 FileReader FileReader 的构造方法接受一个 String 或 File 代表文件名称 为了提高速度, 我们希望使用缓存, 所以, 我们将 FileReader 对象传递给 BufferedReader 的构造方法 BufferedReader 提供 readline() 接口 当阅读到文件结束时,readLine() 返回 null 我们使用这个值退出循环 ReadLine() 在读入行时, 自动将换行符丢弃了, 所以, 我们在用 StringBuffer.append() 时, 增加了换行符 最后, 我们通过调用 close() 方法关闭文件 1b) 显示了如何将 System.in 包装起来, 进行控制台输入的方法 System.in 是一个 InputStream, 而 BufferedReader 构造方法需要的是一个 Reader, 所以我们使用 InputStreamReader 将其转换为 Reader 2) 从内存输入 13-(19/52)

20 s2 包含了文件的所有内容, 我们利用它生成一个 StringReader 我们利用 read() 方法每 次读入一个字符, 并将它送到控制台 值得注意的是 read() 方法将下一个字符作为整 数返回, 所以必须将其转换为 char 3) 格式化内存输入 为了读入格式化的数据, 我们必须使用 DataInputStream 我们通过 String.getBytes() 方 法将 String 转换为字节数组, 然后利用这个数组生成一个 ByteArrayInputStream 当我们从 DataInputStream 每次读入一个字节时, 读入的任何值都是合法的, 所以, 不能通过 readbytes() 的返回值判断输入的终止 我们可以使用 available() 方法检查尚有多少字节 : // Lec13: TestEOF.java import java.io.*; public class TestEOF { // 将异常抛到控制台 public static void main(string[] args) throws IOException { DataInputStream in = new DataInputStream( new BufferedInputStream( new FileInputStream(new File("TestEOF.java")))); while(in.available()!= 0) System.out.print((char)in.readByte()); 注意 available() 方法对不同的输入流产生不同的结果 它返回的数字表示还能从数据源中读入的字节数 用于文件时, 表示文件中剩余的字节数 但对于别的输入流, 如管道, 则意义又有变化 所以, 使用时一定要注意 我们也可以利用异常来检测文件的结果 不过这种做法通常被认为是异常的错误用法 4) 文件输出这个例子也显示了如何将数据写入文件 首先, 我们生成一个 FileWriter 通常我们都希望利用缓存, 所以, 我们又利用这个 FileWriter 对象生成一个 BufferedWriter 最后, 我们又将 BufferedWriter 装饰为一个 PrintWriter 按上述方式生成的文件可作为普通的文本文件阅读 在将每一行写入文件时, 我们加 13-(20/52)

21 上了行号, 注意我们并没有使用 LineNumberInputStream, 因为这是一个愚蠢的类, 一般不用它 例中显示, 跟踪行号实际上是一个非常简单的工作 在输入文件读完之后,readLine() 返回 null 注意必须记得调用 close() 方法, 否则, 因为缓存没有刷新, 文件将不完全 输出流 输出流接其输出格式可分为两大类, 一类是用于人类查看的, 以人类可以辨识的格式输出数据, 另一类则是与 DataInputStream 配套使用的 RandomAccessFile 独立于这两大类, 但是其数据格式与 DataInputStream 和 DataOutputstream 兼容 5) 存储并恢复数据 PrintWriter 以人类可以阅读的格式输出数据 如果我们的目的是输出数据, 然后由另外一个输入流恢复数据, 那么, 我们用 DataOutputStream 保存数据, 用 DataInputStream 恢复数据 如果使用 DataOutputStream 保存数据,Java 保证无论在哪个平台, 我们都可以用 DataInputStream 正确无误的恢复数据 在使用 DataInputStream 和 DataOutputStream 时, 存取 String 对象的可靠的方法是使用 WriteUTF() 方法和 readutf() 方法, 这些方法用 UTF-8 编码保存 String UTF-8 是 Unicode 的一个变种, 它用一个字节保存 ASCII 字符, 用两到三个字节保存非 ASCII 字符, 字符串的长度保存在前两个字节 6) 读写随机访问文件如前面所述,RandomAccessFile 几乎完全与其它 I/O 系统隔绝 它与其它 I/O 系统的唯一共同点就是它实现了 DataInput 和 DataOutput 接口 RandomAccessFile 的构造方法的第二个参数决定文件的读写性, r 表示只读, 而 rw 表示可读可写 因为 Java1.4 的出现, 实际上我们应考虑用内存映射的文件替代 RandomAccessFile 13-(21/52)

22 管道流 目前为止, 我们只是简单第提及了 PipedInputStream,PipedOutputstream,PipedReader, PipedWriter 这不意味着它们不重要, 而是因为只有了解了多线程的概念之后, 我们才能体 会其价值 7. 标准 I/O 标准 I/O 的概念来自于 Unix Unix 程序经常假定其信息来自同一个数据源, 而其结果总是输出到同一个数据汇点, 这就是标准输入和标准输出 程序的错误信息则总是输出到标准错误输出 标准 I/O 的价值在于多个程序可以直接链接起来, 一个程序的标准输出可以变成另一个程序的标准输入, 这是一个非常有用的工具 从标准输入读入 按照标准 I/O 的模式,Java 提供了 System.in,System.out 以及 System.err System.out 和 System.err 已经被包裹为 PrintStream 对象, 而 System.in 则是一个没有任何装饰 的 InputStream 所以为了使用 System.in, 我们必须对它进行必要的装饰 一般情况下, 我们希望从标准输入一次读入一行, 所以, 通常将 System.in 转换为一个 BufferedReader, 然后使用其 readline() 方法 : // Lec13: Echo.java import java.io.*; public class Echo { public static void main(string[] args) throws IOException { BufferedReader in = new BufferedReader( new InputStreamReader(System.in)); String s; while((s = in.readline())!= null && s.length()!= 0) System.out.println(s); 13-(22/52)

23 将 System.out 转换为 PrintWriter System.out 是一个 PrintStream, 不能正确地处理多字节文字 所以有时需要将其转换为 PrintWriter PrintWriter 的一个构造方法接受 OutputStream 对象, 所以, 可以直接转换 : // Lec13: ChangeSystemOut.java import java.io.*; public class ChangeSystemOut { public static void main(string[] args){ PrintWriter out = new PrintWriter(System.out, true); out.println(" 幸福的家庭都很相像, 而不幸的家庭各有各的问题!"); 注意我们必须使用接受两个参数的构造方法, 用第二个参数数据指定其进行自动缓存刷新, 否则, 我们将看不到输出 标准 I/O 重定向 System 类允许我们利用下列简单的方法重定向标准 I/O SetIn(InputStream) SetOut(PrintStream) SetIn(PrintStream) 请看下面的例子 : // Lec13: Redirecting.java import java.io.*; public class Redirecting { public static void main(string[] args) throws IOException { PrintStream console = System.out; BufferedInputStream in = new BufferedInputStream( new FileInputStream("Redirecting.java")); PrintStream out = new PrintStream( new BufferedOutputStream( new FileOutputStream("test.out"))); System.setIn(in); System.setOut(out); BufferedReader br = new BufferedReader( new InputStreamReader(System.in)); String s; 13-(23/52)

24 while((s = br.readline())!= null) System.out.println(s); out.close(); System.setOut(console); System.out.println(" 请察看文件 \"test.out\""); 这个程序将标准输入连接到一个文件, 而将标准输出重新定向到另一个文件 8. 新 I/O Java1.4 中在 java.nio 包中推出了新 I/O, 其主要目的是改善速度 实际上, 老的 I/O 系统在 java1.4 中也已经利用这个新技术重新实现过了 所以, 既或我们不明确使用 nio 的类, 也能 享受 Java1.4 提供的性能改进 Java1.4 利用与操作系统相近的方式处理输入输出 : 通道 (channel) 和缓存 (buffer) 可以将这种新的结构想象为一个煤矿 : 通道是包含了煤层的煤矿, 而 buffer 就像送入煤矿的 推车 推车回来时装满了煤, 我们从车中获得煤, 也就是说我们不直接与通道接触, 而是通 过 buffer 与之接触, 通道可以从 buffer 中取得数据, 也可以将数据装入 buffer 中, 与 Channel 直接接触的 buffer 是 ByteBuffer ByteBuffer 是非常具体的类, 我们在调用其构造方法时, 直接指明 buffer 的大小,ByteBuffer 同时也提供了读写基本数据类型的接口, 但它不提供 String 的读写和其他对象的读写 旧的 I/O 系统中三个类 FileInputStream FileOutputStream 以及 RandomAccessFile 被修改, 通 过方法 getchannel() 产生一个 Filechannel 注意上述三个被修改的流均是面向字节的 Reader 和 Writer 类不生成 Channel 应用程序类 java.nio.channels.channels 提供方法, 将 Channel 转换为 Reader 或 Writer 下面是利用 FileInputStream FileOutputStream 以及 RandomAccessFile 生成 Channel 的例子 // Lec13: GetChannel.java import java.io.*; import java.nio.*; import java.nio.channels.*; 13-(24/52)

25 public class GetChannel { private static final int BSIZE = 1024; private static final String F_NAME = "data.txt"; public static void main(string[] args) throws Exception { // 写文件 FileChannel fc = new FileOutputStream(F_NAME).getChannel(); fc.write(bytebuffer.wrap("hello( 您好 ) ".getbytes())); fc.close(); // 加到文件末尾 fc = new RandomAccessFile(F_NAME, "rw").getchannel(); fc.position(fc.size()); fc.write(bytebuffer.wrap("world( 世界 )!".getbytes())); fc.close(); // 读文件 fc = new FileInputStream(F_NAME).getChannel(); ByteBuffer buff = ByteBuffer.allocate(BSIZE); fc.read(buff); buff.flip(); while(buff.hasremaining()) System.out.print((char)buff.get()); 程序运行时显示 : Hello???????? World????????! 如程序所示,FileInputStream FileOutputStream 以及 RandomAccessFile 的 getchannel() 方法返回一个 FileChannel 对象 我们利用 FileChannel 的 read() 和 write() 方法用 ByteBufferr 访问文件 ( 读写文件 ) 将数据装入 ByteBuffer 的方法之一是利用各种 put 方法将字节数组或基本填入 ByteBuffer 然而, 如程序所示, 我们也可以调用 ByteBuffer.wrap() 方法, 将一字节数组包裹, 形成一个新的 ByteBuffer 在利用 wrap() 生成新的 ByteBuffer 时, 字节数组并没有被复制到 ByteBuffer 中, 它被直接用到 ByteBuffer 中 我们称产生的 ByteBuffer 由字节数组支持 Java.nio 目的是追求更快的速度 所以在从 channel 读取数据时, 我们应使用足够大的 ByteBuffer 我们用 ByteBuffer.allocate() 方法生成一个 ByteBuffer,ByteBuffer 的大小一般为 1024 的倍数 13-(25/52)

26 在调用 Filechannel 的 read() 方法, 将数据装入 ByteBuffer 之后, 应该调用 flip() 方法, 使得缓 存准备好从其中抽取数据 请看如下一个简单的文件拷贝程序 // Lec13: ChannelCopy.java import java.io.fileinputstream; import java.io.fileoutputstream; import java.nio.bytebuffer; import java.nio.channels.filechannel; public class ChannelCopy { private static final int BSIZE = 1024; public static void main(string[] args) throws Exception { if(args.length!= 2) { System.out.println(" 参数 : 源文件目标文件 "); System.exit(1); FileChannel in = new FileInputStream(args[0]).getChannel(), out = new FileOutputStream(args[1]).getChannel(); ByteBuffer buffer = ByteBuffer.allocate(BSIZE); while(in.read(buffer)!= -1) { buffer.flip(); // Prepare for writing out.write(buffer); buffer.clear(); // Prepare for reading 程序中打开了两个 FileChannel, 分别用于读和写 生成了一个 ByteBuffer, 用于读写 当 filechannel.read() 返回 -1 时, 表示已到达输入通道的末端 方法 read() 将数据装入 ByteBuffer 之后,ByteBuffer.flip() 使得该 ByteBuffer 准备妥当, 便于从中提取数据 方法 write() 将 ByteBuffer 中的数据写入该 FileChannel 在调用 write() 之后, 数据仍然保留在 ByteBuffer 之中,clear() 方法将 ByteBuffer 内部的所有指针复位, 便于下次 read() 时接受数据 但是上述数据并不是处理这类事物的最佳的方式 FileChannel 的 transferto() 和 transferfrom() 方法允许我们直接将一个 Channel 连接到另一个 Channel: // Lec13: Transfer.java 13-(26/52)

27 import java.io.*; import java.nio.channels.*; public class Transfer { public static void main(string[] args) throws Exception { if(args.length!= 2){ System.out.println(" 参数 : 源文件目标文件 "); System.exit(1); FileChannel in = new FileInputStream(args[0]).getChannel(); FileChannel out = new FileOutputStream(args[1]).getChannel(); in.transferto(0, in.size(), out); // 或者 out.tranferfrom(in, 0, in.size()); 数据转换 回头看看 GetChannel.Java, 为了打印文件中的信息, 我们每次从 ByteBuffer 中读取一个字节, 然后将其转换为 char, 并打印 这种方式太原始, 而且不能正确处理多字节文字 ByteBuffer 包含的是纯二进制数据, 为了显示其中的内容, 必须对数据进行转换 ( 编码 ) // Lec13: BufferToText.java import java.io.*; import java.nio.*; import java.nio.channels.*; import java.nio.charset.*; public class BufferToText { static abstract class Test { private String name; public static final String TXT = " 包含中文 English 以及 123 数字的文字 "; Test(String n){ name = n; protected ByteBuffer writeandread(bytebuffer in) throws Exception { System.out.println(name); System.out.println("remaining: " + in.remaining()); File file = new File("data2.txt"); FileChannel fc = new FileOutputStream(file).getChannel(); fc.write(in); fc.close(); fc = new FileInputStream(file).getChannel(); ByteBuffer out = ByteBuffer.allocate(1024); fc.read(out); out.flip(); 13-(27/52)

28 fc.close(); return out; protected void check(string s){ System.out.println(" [" + s + "]"); if(txt.equals(s)) System.out.println("...OK"); else System.out.println("...Error"); public abstract void test() throws Exception; static Test[] tests = { new Test("1 不做转换 "){ public void test() throws Exception { ByteBuffer out = writeandread(bytebuffer.wrap(txt.getbytes())); check(out.ascharbuffer().tostring());, new Test("2 读出后用当前缺省字符集解码 "){ public void test() throws Exception { Charset cs = Charset.forName(System.getProperty("file.encoding")); ByteBuffer out = writeandread(bytebuffer.wrap(txt.getbytes())); String result = cs.decode(out).tostring(); check(result);, new Test("3 写入前用 UTF-16BE 编码 "){ public void test() throws Exception { Charset cs = Charset.forName("UTF-16BE"); ByteBuffer in = cs.encode(txt); ByteBuffer out = writeandread(in); check(out.ascharbuffer().tostring());, new Test("4 用 getbytes() 编码 "){ public void test() throws Exception { ByteBuffer out = writeandread( ByteBuffer.wrap(TXT.getBytes("UTF-16BE"))); check(out.ascharbuffer().tostring());, new Test("5 通过 CharBuffer 写入 "){ public void test() throws Exception { ByteBuffer in = ByteBuffer.allocate(100); 13-(28/52)

29 in.ascharbuffer().put(txt); ByteBuffer out = writeandread(in); check(out.ascharbuffer().tostring());, ; public static void main(string[] args) throws Exception { for(int i=0; i<tests.length; i++) tests[i].test(); 该程序在运行时显示 : 1 不做转换 remaining: 34 [?????? 杬楳棒????????]...Error 2 读出后用当前缺省字符集解码 remaining: 34 [ 包含中文 English 以及 123 数字的文字 ]...OK 3 写入前用 UTF-16BE 编码 remaining: 44 [ 包含中文 English 以及 123 数字的文字 ]...OK 4 用 getbytes() 编码 remaining: 44 [ 包含中文 English 以及 123 数字的文字 ]...OK 5 通过 CharBuffer 写入 remaining: 100 [ 包含中文 English 以及 123 数字的文字...Error 在第一个测试中, 我们试着用 ByteBuffer 的 ascharbuffer() 方法将 ByteBuffer 转换为 CharBuffer, 然后显示 CharBuffer 的内容, 结果证明, 这种办法并不能正确显示 在第二个测试中, 从文件读出数据之后, 我们利用系统当前的缺省字符集对其进行解码 运 行结果正确 System.getProperty("file.ercoding") 返回了当前字符集的名称 CharSet.decode() 接受一个 ByteBuffer, 将其解码, 返回一个 CharBuffer 在第三个测试中, 我们利用 CharSet.encode(String) 方法, 对字符串中的信息进行编码, 其返 13-(29/52)

30 回结果为 ByteBuffer 运行结果正确 第四个测试中展示了另外一种编码方法 : 利用 String.getBytes(String) 方法 第五个测试中我们利用 CharBuffer 来写入数据, 从结果看出, 尽管我们写的信息是可见的形式出现了, 但是 CharBuffer 中空闲的空间也被 ByteBuffer 当作有用的信息接受了过来 处理基本数据类型 尽管 ByteBuffer 只存储二进制数据, 但它却提供方法处理各基本类型的数据 下面的例子利 用这些方法将基本类型的数据插入 ByteBuffer 以及从 ByteBuffer 读取基本数据类型的数据 // Lec13: GetData.java import java.nio.*; public class GetData { public static void main(string[] args){ ByteBuffer buff = ByteBuffer.allocate(1024); buff.putchar('a'); buff.putshort((short)23); buff.putdouble( ); buff.flip(); System.out.println(buff.getChar()); System.out.println(buff.getShort()); System.out.println(buff.getDouble()); 程序运行时显示 : A Buffer 内幕 Buffer 由数据以及四个变址组成 四个变址是 mark positon limit capacity mark position 标记, 用于记住某一位置 表示 Buffer 中当前的指针, 是每次写入或提取数据的位置 13-(30/52)

31 mark limit capacity 标记, 用于记住某一位置 有两个用途 : 在写入时,limit 表示写入的范围, 我们只能从 position 位置开始写入, 至到 limit 为止 如果写入过程中, 导致 position 到达 limit 所指的位置, 那么, 会产生异常 在写入完毕后, 为了从中提取数据, 要求调用 flip() 方法, 该方法将 limit 指向当前 position 所指的位置, 而将 position 设置为 0 由此, 可以从 0 开始提取数据, 直到 limit 为止 方法 remainning() 返回的数据实际上就是 limit-position 表示 Buffer 的容量, 一旦生成就保持不变 Buffer 还提供了几个方法, 可以查询或设置上述几个变址, 其中,limit() 返回当前的 limit 值, 而 limit(int) 方法设置 limit 值 同样 position() 方法返回当前 position 的值, 而 position(int) 设置 position 的值 方法 mark() 则将 mark 值设置为当前的 position 值 在调用 reset() 方法时,position 就恢复为 mark 的值 方法 clear() 将 position 设置为 0, 而将 limit 设置为 capacity 如前所述,flip() 的作用是将 limit 设置为当前的 position 值 而将 position 设置为 0, 这意味着如果连续调用两次 flip() 方法, 则 Buffer 的 position 和 limit 都将为 0, 从而既不能写入也无法读出 内存映像文件 内存映像文件, 允许我们生成并处理那些太大, 不能完全装入内存的文件 使用内存映像文件时, 我们可以认为整个文件都在内存中, 所以可以当作一个非常大的数组 来处理它 这种方式极大地简化了文件处理 下面是一个简单的示例 : // Lec13: LargeMappedFile.java import java.io.randomaccessfile; import java.nio.mappedbytebuffer; import java.nio.channels.filechannel; public class LargeMappedFile { 13-(31/52)

32 static int length = 0x8FFFFFF; // 128 Mb public static void main(string[] args) throws Exception { MappedByteBuffer out = new RandomAccessFile("test.dat", "rw").getchannel().map(filechannel.mapmode.read_write, 0, length); for(int i = 0; i < length; i++) out.put((byte)'x'); System.out.println("Finished writing"); for(int i = length/2; i < length/2 + 6; i++) System.out.print((char)out.get(i)); 为了进行读写, 我们首先生成一个 RandomAccessFile, 然后生成一个 channel, 并用该 Channel 的 map() 方法生成一个 MappedByteBuffer MappedByteBuffer 实际上是 Buffer 的一种特例, 所以具有 Buffer 的所有接口 在生成 MappedByteBuffer 时, 需要指明文件中映像的区域的起始位置和长度 这实际上也意味着我们可以选择映像一个大的文件的一部分到内存 性能 尽管旧的输入输出流系统已经利用 nio 技术更新了, 映像文件的读写速度还是比输入输出流 快得很多 下列程序进行简单的性能比较 // Lec13: MappedIO.java import java.io.*; import java.nio.*; import java.nio.channels.*; public class MappedIO { private static int numofints = ; private abstract static class Tester { protected File file = new File("tmp.dat"); private String name; public Tester(String s){ name = s; public long runtest(){ System.out.print(name + ": "); try{ long t1 = System.currentTimeMillis(); test(); long t2 = System.currentTimeMillis(); System.out.println(t2-t1); return (t2-t1); catch(ioexception e){ 13-(32/52)

33 throw new RuntimeException(e); public abstract void test() throws IOException; private static Tester[] tests = { new Tester("Stream Write"){ public void test() throws IOException { DataOutputStream dos = new DataOutputStream( new BufferedOutputStream( new FileOutputStream(file))); for(int i=0; i<numofints; i++) dos.writeint(i); dos.close();, new Tester("Mapped Write"){ public void test() throws IOException { FileChannel fc = new RandomAccessFile(file, "rw").getchannel(); IntBuffer ib = fc.map(filechannel.mapmode.read_write, 0, numofints * 4).asIntBuffer(); for(int i=0; i<numofints; i++) ib.put(i); fc.close();, new Tester("Stream Read"){ public void test() throws IOException { DataInputStream dis = new DataInputStream( new BufferedInputStream( new FileInputStream(file))); for(int i=0; i<numofints; i++) dis.readint(); dis.close();, new Tester("Mapped Read"){ public void test() throws IOException { FileChannel fc = new FileInputStream(file).getChannel(); IntBuffer ib = fc.map(filechannel.mapmode.read_only, 0, fc.size()).asintbuffer(); for(int i=0; i<numofints; i++) ib.get(); fc.close();, new Tester("Stream Read/Write"){ public void test() throws IOException { RandomAccessFile raf = new RandomAccessFile(file, "rw"); raf.writeint(1); 13-(33/52)

34 for(int i=0; i<numofints; i++){ raf.seek(raf.length()-4); raf.writeint(raf.readint()); raf.close();, new Tester("Mapped Read/Write"){ public void test() throws IOException { FileChannel fc = new RandomAccessFile(file, "rw").getchannel(); IntBuffer ib = fc.map(filechannel.mapmode.read_write, 0, fc.size()).asintbuffer(); ib.put(0); for(int i=1; i<numofints; i++) ib.put(ib.get(i-1)); fc.close();, ; public static void main(string[] args){ for(int i=0; i<tests.length; i++) tests[i].runtest(); 这个程序在不同的情况下, 运行结果可能有所变化 下列是一次运行的结果 : Stream Write: 31 Mapped Write: 16 Stream Read: 16 Mapped Read: 0 Stream Read/Write: 1766 Mapped Read/Write: 15 从这个结果看, 尽管映像文件的初始化成本较大, 但总体性能比旧的 I/O 系统要好出很多 程序中, 内部类映像 Tester 提供了测试的基本框架 runtest() 方法提供了测试的流程, 每个具体测试类必须提供的方法 test() 就是具体的测试内容 如程序中所示, 映像写入必须使用 RandomAccessFile 来生成 Channel, 而不能使用 FileOutputStream 文件锁闭 JDK1.4 引入了文件锁闭的概念, 利用文件锁闭的机制, 可以同步对共享文件资源的访问 Java 文件锁闭直接映射到操作系统的锁闭功能, 所以, 哪怕共享资源的别的线程不是 Java 实现的 它也能感受到文件锁闭的作用 13-(34/52)

35 // Lec13: FileLocking.java import java.io.fileoutputstream; import java.nio.channels.filelock; public class FileLocking { public static void main(string[] args) throws Exception { FileOutputStream fos = new FileOutputStream("file.txt"); FileLock fl = fos.getchannel().trylock(); if(fl!= null) { System.out.println("Locked File"); Thread.sleep(10000); fl.release(); System.out.println("Released Lock"); fos.close(); 我们通过 trylock() 或 lock() 方法获得对整个文件的锁闭 trylock() 是非阻塞形的方法, 如果锁闭成功, 它返回一个 Filelock, 如果锁闭失败, 则返回 null 方法 lock() 是阻塞形的, 只有获得了对资源的锁闭, 才返回一个 Filelock 我们通过方法 Filelock.release() 释放对资源的锁闭 9. 压缩 JavaI/O 系统还包含支持读写压缩格式的文件的类 这些类都通过包裹已有的 I/O 类来提供压缩功能 这些类不是派生的 Reader 和 Writer, 而是派生自 InputStream 和 OutputStream 体系, 这是因为压缩是按字节而不是按字符工作的 压缩类 CheckedInputStream CheckedInputStream DeflaterOutputStream ZipOutputStream GZIPOutputStream 功能为任何 InputStream 产生校验码为任何 OutputStream 生成校验码压缩类的基类按 zip 文件格式压缩按 GZIP 文件格式压缩 13-(35/52)

36 压缩类 InflaterInputStream ZipInputStream GzipInputStream 解压类的基类 解压 zip 文件 解压 Gzip 文件 功能 尽管有许多压缩算法, 但 zip 和 GZIP 大概是最常用的 生成 GZIP 压缩文件 GZIP 文件的接口非常简单, 适于压缩单一数据源的数据 // Lec13: GZIPcompress.java import java.io.*; import java.util.zip.*; public class GZIPcompress { public static void main(string[] args) throws IOException { if(args.length == 0){ System.out.println( " 用法 : java GZIPcompress 被压缩的文件名称 \n" + " 使用 GZIP 压缩算法将文件压缩到 test.gz"); System.exit(1); BufferedReader in = new BufferedReader(new FileReader(args[0])); PrintWriter out = new PrintWriter( new BufferedWriter( new OutputStreamWriter( new GZIPOutputStream( new FileOutputStream("test.gz"))))); System.out.println("Writing file"); String s; while((s = in.readline())!= null) out.println(s); in.close(); out.close(); System.out.println("Reading file"); BufferedReader in2 = new BufferedReader( new InputStreamReader( new GZIPInputStream( new FileInputStream("test.gz")))); while((s = in2.readline())!= null) System.out.println(s); 13-(36/52)

37 使用压缩类的方法非常简单 : 只要将输出流包裹到 GZIPOutputStream 或 ZipOutputStream 之 中即可 剩下的只是普通的 I/O 操作 在本例中, 我们故意将面向字节或面向字符的方式混 合在了一起 10. 对象串行化 Java 的对象串行化将任何实现了 Serializable 接口的对象转换为一组字节, 而反过来, 又可以 用这组字节重新构成这个对象 将对象串行化之后, 我们获得的是一组字节, 可以随意处置 比如, 写入文件, 通过网络传 递给另一台电脑等等 串行化只保持对象的非静态成员变量, 而不保存任何成员方法或静态成员变量 如果一个对象实现了 Serializable 接口, 则串行化这个对象就非常简单 : 生成一个 OutputStream, 然后将这个 OutputStream 对象用 ObjectOutputstream 包裹, 调用 writeobject() 方法, 这个对象就被串行化, 并送到 OutputsStream 反串行化的过程很简单 : 用 ObjectInputStream 包裹一个 InputStream, 然后调用 readobject() 即可 串行化非常聪明的地方是, 它不仅保存了这个对象, 同时也保存了对象中引用到的别的所有 对象 下面的例子用互相连接的 虫子 对象作为测试对象, 演示了 Java 串行化的功能 // Lec13: Worm.java import java.io.*; import java.util.*; class Data implements Serializable { private int n; public Data(int n){ this.n = n; public String tostring(){ return Integer.toString(n); 13-(37/52)

38 public class Worm implements Serializable { private static Random rand = new Random(); private Data[] d = { new Data(rand.nextInt(10)), new Data(rand.nextInt(10)), new Data(rand.nextInt(10)), new Data(rand.nextInt(10)), new Data(rand.nextInt(10)), ; private Worm next; private char c; public Worm(int i, char x){ System.out.println("Constructing Worm, i = " + i + ", c = " + x); c = x; if(--i > 0) next = new Worm(i, (char)(x+1)); public String tostring(){ String s = ":" + c + "("; for(int i=0; i<d.length; i++) s += d[i]; s += ")"; if(next!= null) s += next; return s; // Lec13: Save.java import java.io.*; public class Save { static void usage(string s){ System.out.println( " 错误 : " + s + "\n" + " 正确用法 : Save filename\n"); System.exit(1); public static void main(string[] args) throws Exception { if(args.length!= 1) usage(" 没有参数!"); File file = new File(args[0]); File parent = file.getparentfile(); if(parent!= null &&!parent.exists()){ if(!parent.mkdir()) usage(" 无法生成文件 : " + parent); Worm w = new Worm(6, 'a'); ObjectOutputStream out = new ObjectOutputStream( new BufferedOutputStream( 13-(38/52)

39 new FileOutputStream(file))); String s = "Worm Storage"; out.writeobject(s); out.writeobject(w); System.out.println("Saved:"); System.out.println(s); System.out.println(w); out.close(); // Lec13: Restore.java import java.io.*; public class Restore { static void usage(){ System.out.println(" 用法 : java Restore filename\n"); System.exit(1); public static void main(string[] args) throws Exception { if(args.length!= 1) usage(); File file = new File(args[0]); if(!file.exists()) usage(); ObjectInputStream in = new ObjectInputStream( new BufferedInputStream( new FileInputStream(file))); System.out.println("Restored: "); while(true){ try{ System.out.println(in.readObject()); catch(ioexception e){ break; 为了使例子有趣,Worm 对象中包含了一个 Data 对象的数组, 其中每个元素都是随机产生的 每段 Worm 用一个字符标示, 在生成 Worm 时, 构造方法的第一个参数决定 Worm 的长度 在初始化数据成员 next 时, 用减了一的长度调用构造方法, 用 next=null 表示 worm 的结束 上面所有这些是为了使的对象 worm 足够复杂 对于这样一个复杂的对象, 如果由我们负责将其适当保存起来, 其复杂性是可想而知的 但是利用 Java 对象串形化, 事情就变得十分 13-(39/52)

40 简单, 我们只要调用 WriteObject() 方法即可 下面是一次执行产生的结果 >java Save invent\wormsave.dat Constructing Worm, i = 6, c = a Constructing Worm, i = 5, c = b Constructing Worm, i = 4, c = c Constructing Worm, i = 3, c = d Constructing Worm, i = 2, c = e Constructing Worm, i = 1, c = f Saved: Worm Storage :a(42944):b(38473):c(15549):d(22818):e(52299):f(17186) >java Restore invent\wormsave.dat Restored: Worm Storage :a(42944):b(38473):c(15549):d(22818):e(52299):f(17186) 从结果可以看出, 在执行 Restore 时, 并没有调用 worm 的构造方法, 整个对象是直接从 InputeStream 中获得的数据恢复而来的 对象串行化是面向字节的, 所以使用的是 InputStream 和 OutputStream 体系 恢复对象 那么, 如果在解串过程中不使用构造方法, 我们必须知道什么才能正确恢复一个对象呢? 比如, 如果我们串行化一个对象, 然后将结果通过网络传送给另外一台计算机, 那台机器能否仅靠这个串行化的数据重新这个对象呢? 为了回答这个问题, 我们将 Restore.class 文件拷贝到 invent 文件夹, 然后执行 > java Restore WormSave.dat 这时, 程序只能读出 String 对象, 接着就产生一个 ClassNotFoundException 异常, 表示它无 法恢复读到的对象 : Restored: Worm Storage java.lang.classnotfoundexception: Worm at java.net.urlclassloader$1.run(unknown Source) at java.security.accesscontroller.doprivileged(native Method) at java.net.urlclassloader.findclass(unknown Source) at java.lang.classloader.loadclass(unknown Source) 13-(40/52)

41 at sun.misc.launcher$appclassloader.loadclass(unknown Source) at java.lang.classloader.loadclass(unknown Source) at java.lang.classloader.loadclassinternal(unknown Source) at java.lang.class.forname0(native Method) at java.lang.class.forname(unknown Source) at java.io.objectinputstream.resolveclass(unknown Source) at java.io.objectinputstream.readnonproxydesc(unknown Source) at java.io.objectinputstream.readclassdesc(unknown Source) at java.io.objectinputstream.readordinaryobject(unknown Source) at java.io.objectinputstream.readobject0(unknown Source) at java.io.objectinputstream.readobject(unknown Source) at Restore.main(Restore.java:21) 如果我们再将 Worm.class 文件和 Data.class 文件复制到 invent 文件夹, 然后在此文件夹下执 行 > java Restore WormSave.dat 我们看到 worm 对象也被正常恢复了 由此可见, 能够恢复对象的先决条件是 JVM 必须能够 找到相关类的.class 文件 11. 正则表达式 Java1.4 中增加正则表达式的处理能力 什么是正则表达式? 正则表达式是字符串处理工具, 常见于 Unix 应用程序如 sed,awk 等 正则表达式允许我们在程序中指定字符串的样式, 按这些样式去匹配, 进行适当的处理 生成正则表达式 我们首先介绍一些常用的正则表达式构件 可从 java.util.regex.pattern 的文档中找到全部的构件 Summary of regular-expression constructs Construct Matches Characters x The character x 13-(41/52)

42 \\ The backslash character \0n The character with octal value 0n (0 <= n <= 7) \0nn The character with octal value 0nn (0 <= n <= 7) \0mnn The character with octal value 0mnn (0 <= m <= 3, 0 <= n <= 7) \xhh The character with hexadecimal value 0xhh \uhhhh The character with hexadecimal value 0xhhhh \t The tab character ('\u0009') \n The newline (line feed) character ('\u000a') \r The carriage-return character ('\u000d') \f The form-feed character ('\u000c') \a The alert (bell) character ('\u0007') \e The escape character ('\u001b') \cx The control character corresponding to x Character classes [abc] [^abc] [a-za-z] [a-d[m-p]] [a-z&&[def]] [a-z&&[^bc]] [a-z&&[^m-p]] a, b, or c (simple class) Any character except a, b, or c (negation) a through z or A through Z, inclusive (range) a through d, or m through p: [a-dm-p] (union) d, e, or f (intersection) a through z, except for b and c: [ad-z] (subtraction) a through z, and not m through p: [a-lq-z](subtraction) Predefined character classes. Any character (may or may not match line terminators) \d A digit: [0-9] \D A non-digit: [^0-9] \s A whitespace character: [ \t\n\x0b\f\r] \S A non-whitespace character: [^\s] \w A word character: [a-za-z_0-9] \W A non-word character: [^\w] POSIX character classes (US-ASCII only) \p{lower A lower-case alphabetic character: [a-z] \p{upper An upper-case alphabetic character:[a-z] \p{ascii All ASCII:[\x00-\x7F] \p{alpha An alphabetic character:[\p{lower\p{upper] \p{digit A decimal digit: [0-9] 13-(42/52)

43 \p{alnum \p{punct \p{graph \p{print \p{blank \p{cntrl \p{xdigit \p{space An alphanumeric character:[\p{alpha\p{digit] Punctuation: One ~ A visible character: [\p{alnum\p{punct] A printable character: [\p{graph\x20] A space or a tab: [ \t] A control character: [\x00-\x1f\x7f] A hexadecimal digit: [0-9a-fA-F] A whitespace character: [ \t\n\x0b\f\r] java.lang.character classes (simple java character type) \p{javalowercase Equivalent to java.lang.character.islowercase() \p{javauppercase Equivalent to java.lang.character.isuppercase() \p{javawhitespace Equivalent to java.lang.character.iswhitespace() \p{javamirrored Equivalent to java.lang.character.ismirrored() Classes for Unicode blocks and categories \p{ingreek A character in the Greek block (simple block) \p{lu An uppercase letter (simple category) \p{sc A currency symbol \P{InGreek Any character except one in the Greek block (negation) [\p{l&&[^\p{lu]] Any letter except an uppercase letter (subtraction) Boundary matchers ^ The beginning of a line $ The end of a line \b A word boundary \B A non-word boundary \A The beginning of the input \G The end of the previous match \Z The end of the input but for the final terminator, if any \z The end of the input Greedy quantifiers( 贪婪的, 贪心的 ) X? X, once or not at all X* X, zero or more times X+ X, one or more times X{n X, exactly n times X{n, X, at least n times 13-(43/52)

44 X{n,m X, at least n but not more than m times Reluctant quantifiers( 懒惰的 ) X?? X, once or not at all X*? X, zero or more times X+? X, one or more times X{n? X, exactly n times X{n,? X, at least n times X{n,m? X, at least n but not more than m times Possessive quantifiers( 有占有欲的 ) X?+ X, once or not at all X*+ X, zero or more times X++ X, one or more times X{n+ X, exactly n times X{n,+ X, at least n times X{n,m+ X, at least n but not more than m times Logical operators XY X Y (X) X followed by Y Either X or Y X, as a capturing group Back references \n Whatever the n th capturing group matched Quotation \ Nothing, but quotes the following character \Q Nothing, but quotes all characters until \E \E Nothing, but ends quoting started by \Q Special constructs (non-capturing) (?:X) X, as a non-capturing group (?idmsux-idmsux) Nothing, but turns match flags on - off (?idmsux-idmsux:x) X, as a non-capturing group with the given flags on - off (?=X) X, via zero-width positive lookahead (?!X) X, via zero-width negative lookahead (?<=X) X, via zero-width positive lookbehind 13-(44/52)

45 (?<!X) (?>X) X, via zero-width negative lookbehind X, as an independent, non-capturing group Pattern 和 Matcher 下面的例子可以作为对正则表达式的测试程序, 第一个参数是字符串, 后面的参数则是正则 表达式 // Lec13: TestRegularExpression.java import java.util.regex.*; public class TestRegularExpression { public static void main(string[] args){ if(args.length < 2){ System.out.println( " 用法 : TestRegularExpression 字符串正则表达式 "); System.exit(0); System.out.println("Input:\"" + args[0] + "\""); for(int i=1; i<args.length; i++){ System.out.println("\nRegular expression: \"" + args[i] + "\""); Pattern p = Pattern.compile(args[i]); Matcher m = p.matcher(args[0]); while(m.find()){ System.out.println("Match \"" + m.group() + "\" at position " + m.start() + "-" + (m.end()-1)); 按下列命令运行程序 : > java TestRegularExpression All happy families are all alike \w+\s 程序运行显示 : Input:"All happy families are all alike" Regular expression: "\w+\s" Match "All " at position 0-3 Match "happy " at position 4-9 Match "families " at position Match "are " at position Match "all " at position (45/52)

46 Java 利用 Pattern 和 Matcher 两个类实现正则表达式的功能 Pattern 是经过编译的正则表达式, 静态方法 Pattern.compile() 将一个正则表达式编译生成一个 Pattern 对象 正如上述例子中所示, 我们 Pattern 对象的 matcher() 方法以及输入字符串, 生成一个 Matcher 对象 Pattern 也有一个 static boolean matcher(string regex, charsequence input) 方法, 用于快速查阅 regex 可否能在 input 中找到, 另有一个 split() 方法, 该方法生成由于匹 配 regex 而将输入字符串分解而成的字符串数组 其中数组元素是在原输入字符串中提取匹 配字符串后所剩下的字符串 程序中通过给 Pattern.matcher() 方法传递输入字符串, 而获得 Matcher 对象 我们利用 Matcher 对象来访问结果 Matcher 提供如下方法 boolean matcher() boolean lookingat() boolean find() boolean find(int start) 当正则表达式 Pattern 与整个输入字符串相匹配, 则 matcher() 返回 true 如果输入字符串从头开始是一个匹配时,lookingAt() 返回 true find() Matcher.find() 可用于找到多个匹配 find() 方法就像一个迭代器, 能够遍历整个输入字符串 find() 的另一个版本则接受一个整数, 用这个整数指定在输入串中开始匹配的位置 Pattern 标志选项 Pattern.compile() 方法的另一个版本接受不同的标志选项, 改变正则表达式匹配的行为 : Pattern Pattern.compile(String input, int flag) 其中 flag 可能的取值由 Pattern 的如下常量给出 : 13-(46/52)

47 Compile 标志 CANON_EQ CASE_INSENSITIVE COUMENTS DOTALL MULTILINE UNICODE_CASE UNIX_LINES 效果只有两个字符的正规分解相匹配时, 这两个字符才相配 缺省情况下,CASE_INSENSITIVE 模式下处理的输入字串是 ASCII 串 该标志允许我们不分大小写匹配在这个模式下, 空格被忽视, 嵌入的以 # 开始的注释行也被忽视在 DOTALL 模式下, 表达式. 与任何字符相匹配, 包括行的结束符 而缺省模式下,. 与行的结束符不匹配在多行模式下, 表达式 ^ 和 $ 分别表示行的开始和结束, ^ 同时也可与输入串的开始匹配, $ 与输入串的结束相匹配 在缺省模式下, ^ 和 $ 只与整个输入串的开始和结束相匹配指定这个标志后, 不分大小写 匹配是在 Unicode 基础上进行的在这个模式下, 只有 \n 行结束串符能被. 以及 ^ 识别 split() split() 方法从输入串中将与正则表达式相匹配的字符提取之后, 用剩余的字符串形成 String 数组 // Lec13:regex: SplitDemo.java import java.util.arrays; import java.util.regex.pattern; public class SplitDemo { public static void main(string[] args) { String input = "This!!unusual use!!of exclamation!!points"; System.out.println(Arrays.asList( Pattern.compile("!!").split(input))); // Only do the first three: System.out.println(Arrays.asList( Pattern.compile("!!").split(input, 3))); System.out.println(Arrays.asList( "Aha! String has a split() built in!".split(" "))); 该程序在运行时显示 : [This, unusual use, of exclamation, points] 13-(47/52)

48 [This, unusual use, of exclamation!!points] [Aha!, String, has, a, split(), built, in!] 第二个 splite() 限制了分解的次数 正规表达式非常有用, 所以有些功能已直接实现在 String 类中, 比如 splite() matches() replacefirst() replaceall() 等 替换操作 在寻找并替换字符串时, 正规表达式格外有用 我们常用的替换方法有 : replacefirst(string replacement) 用 replacement 替换输入串中的第一个匹配的部分 replaceall(string replacement) 用 replacement 替换输入串中的每个匹配的部分 AppendReplacement(StringBuffer sbuf, String replacement) 按步骤替换并写入 sbuf 中 appendtail(stringbuffer sbuf, String replacement) 下面的例子显示了各种替换操作的用法 程序首先利用正规表达式将文件中的注释块提取出 来, 用作程序其余部分的输入串 import java.io.file; // Lec13:regex: TheReplacements.java import java.util.regex.matcher; import java.util.regex.pattern; import net.effortech.harry.util.textfile; /*! Here's a block of text to use as input to the regular expression matcher. Note that we'll first extract the block of text by looking for the special delimiters, then process the extracted block.!*/ public class TheReplacements { public static void main(string[] args) throws Exception { String s = TextFile.read(new File("regex\\TheReplacements.java")); 13-(48/52)

49 // Match the specially-commented block of text above: Matcher minput = Pattern.compile("/\\*!(.*)!\\*/", Pattern.DOTALL). matcher(s); if(minput.find()) s = minput.group(1); // Captured by parentheses // Replace two or more spaces with a single space: s = s.replaceall(" {2,", " "); // Replace one or more spaces at the beginning of each // line with no spaces. Must enable MULTILINE mode: s = s.replaceall("(?m)^ +", ""); System.out.println(s); s = s.replacefirst("[aeiou]", "(VOWEL1)"); StringBuffer sbuf = new StringBuffer(); Pattern p = Pattern.compile("[aeiou]"); Matcher m = p.matcher(s); // Process the find information as you // perform the replacements: while(m.find()) m.appendreplacement(sbuf, m.group().touppercase()); // Put in the remainder of the text: m.appendtail(sbuf); System.out.println(sbuf); 程序运行时显示 : Here's a block of text to use as input to the regular expression matcher. Note that we'll first extract the block of text by looking for the special delimiters, then process the extracted block. H(VOWEL1)rE's A block Of text to UsE As InpUt to the regular ExprEssIOn matcher. NOtE that we'll first ExtrAct the block Of text by looking for the special delimiters, then process the ExtrActEd block. 1) 我们用 TextFile.read() 将 Replacments.java 文件的内容内读入到 String 对象之中, 用作程序中其它地方的输入串 2) minput 是一个用正则表达式 /\\*!(.*)!\\*/" 生成的匹配器 这个正则表达式代表了以 /*!" 开头, 以!*/" 结束的任何字符串, 所以当 s 作为输入串匹配时, 我们就获得了程序中位于 /*!" 和!*/" 之间的文字 13-(49/52)

50 3) 我们利用 String.replacAll() 方法, 将两个以上空格替换为单个空格 4) 利用 String.replacAll() 方法, 删除每行开头的空格 5) 利用 String.replacFirst() 方法, 将第一个元音字母替换为 (VOWEL1) 6) 利用 matcher.appendreplacement() 将所有的元音字母替换为对应的大写字母 正规表达式与 JavaI/O 目前为止的所有例子中, 正规表达式都用于静态字符串, 下面的例子显示了将正规表达式用 于文件匹配的方法 Grep.java 接受两个参数, 其中第一个是文件名称, 第二个是需要查找的 正规表达式 程序作为输出, 显示匹配文字串的行以及匹配的位置 // Lec13: Grep.java import java.io.*; import java.util.regex.*; import java.util.*; import net.effortech.harry.util.*; public class Grep { public static void main(string[] args) throws Exception { if(args.length!= 2){ System.out.println("Usage: java Grep file regex"); System.exit(1); Pattern p = Pattern.compile(args[1]); ListIterator it = Arrays.asList( TextFile.read( new File(args[0])).split("\n")).listIterator(); while(it.hasnext()){ String s = (String)it.next(); Matcher m = p.matcher(s); while(m.find()) System.out.println(it.nextIndex() + ": " + m.group() + " + m.start() + "-" + (m.end()-1)); 我们用 TextFile.read() 方法读入文件, 并用 String.split() 方法按 \n 将整个文字内容分解为字 13-(50/52)

51 符串数组, 然后转换为 ArrayList. 我们用 ListIterator 遍布整个 ArrayList, 其中每一项对应文件中的行 对应于每一行, 我们利用 Patternmatcher() 生成一个匹配器, 然后用 find() 寻找匹配 执行下列命令, > java Grep regex\thereplecements.java \w{8,+\. 时, 显示如下结果 : 2: : : : StringTokenizer 还有用吗? 在 java 1.4 之前, 我们利用 StringTokenizer 类来分解字符串 但是, 在介绍了正则表达式之 后, 实际上利用正则表达式分解字符串更加简明 方便 : // Lec13:regex: ReplacingStringTokenizer.java import java.util.*; public class ReplacingStringTokenizer { public static void main(string[] args){ String input = "All happy families are alike, but an " + "unhappy family is unhappy after its own fashion."; StringTokenizer stoke = new StringTokenizer(input); System.out.println("\nStringTokenizer:"); while(stoke.hasmoreelements()) System.out.println(stoke.nextToken()); System.out.println("\nregular expression: "); System.out.println(Arrays.asList(input.split("[\\s.,]+"))); 该程序运行时显示 : StringTokenizer: All happy families 13-(51/52)

52 are alike, but an unhappy family is unhappy after its own fashion. regular expression: [All, happy, families, are, alike, but, an, unhappy, family, is, unhappy, after, its, own, fashion] 利用正规表达式, 我们还可以按非常复杂的方式分解字符串, 而用 StringTokenizer 分解的方 式就受到极大的限制 13-(52/52)

OOP with Java 通知 Project 6: 5 月 30 日晚 9 点

OOP with Java 通知 Project 6: 5 月 30 日晚 9 点 OOP with Java Yuanbin Wu cs@ecnu OOP with Java 通知 Project 6: 5 月 30 日晚 9 点 复习 异常处理 语法 抛出异常 : throw 处理异常 : try, catch 异常对象 : Exception 类的子类 从方法中抛出异常 方法的异常说明 :throws 中断当前方法的执行, 返回抛出的异常对象, 在该方法的调用路径上寻找合适的

More information

OOP with Java 通知 Project 6: 5 月 24 日晚 9 点

OOP with Java 通知 Project 6: 5 月 24 日晚 9 点 OOP with Java Yuanbin Wu cs@ecnu OOP with Java 通知 Project 6: 5 月 24 日晚 9 点 复习 异常处理 语法 抛出异常 : throw 处理异常 : try, catch 异常对象 : Exception 类的子类 从方法中抛出异常 方法的异常说明 :throws 中断当前方法的执行, 返回抛出的异常对象, 在该方法的调用路径上寻找合适的

More information

OOP with Java 通知 Project 6: 6 月 6 日晚 9 点

OOP with Java 通知 Project 6: 6 月 6 日晚 9 点 OOP with Java Yuanbin Wu cs@ecnu OOP with Java 通知 Project 6: 6 月 6 日晚 9 点 复习 异常处理 语法 抛出异常 : throw 处理异常 : try, catch 异常对象 : Exception 类的子类 从方法中抛出异常 方法的异常说明 :throws 中断当前方法的执行, 返回抛出的异常对象, 在该方法的调用路径上寻找合适的

More information

Java Access 5-1 Server Client Client Server Server Client 5-2 DataInputStream Class java.io.datainptstream (extends) FilterInputStream InputStream Obj

Java Access 5-1 Server Client Client Server Server Client 5-2 DataInputStream Class java.io.datainptstream (extends) FilterInputStream InputStream Obj Message Transition 5-1 5-2 DataInputStream Class 5-3 DataOutputStream Class 5-4 PrintStream Class 5-5 (Message Transition) (Exercises) Java Access 5-1 Server Client Client Server Server Client 5-2 DataInputStream

More information

while ((ch = fr.read())!= -1) { System.out.print((char) ch); fr.close(); 例 3: 用 BufferedReader 读 TXT 文件 public class FileReaderDemo3 { public static v

while ((ch = fr.read())!= -1) { System.out.print((char) ch); fr.close(); 例 3: 用 BufferedReader 读 TXT 文件 public class FileReaderDemo3 { public static v 第九章 Java I/O 流操作 实验目的 (1) 掌握文本文件的读写方法 (2) 掌握 InputStream OutputStream 的使用方法 (3) 熟悉 FileReader,BufferedReader,InputStreamReader 和 FileWriter, BufferedWriter, PrintWriter 的使用方法 ; 理解使用过滤流实现数据项的读写 :DataOutputStream,

More information

untitled

untitled Velocity 14 100061 315@pptph.com.cn http://www.pptph.com.cn 010-67129212 010-67129211 787 1092 1/16 22 535 1 0 000 2001 11 1 2001 11 1 ISBN 7-115-09828-X/TP 2577 32.00 01067129223 1 2 1 2 3 4 5 1 Velocity

More information

Guava学习之Resources

Guava学习之Resources Resources 提供提供操作 classpath 路径下所有资源的方法 除非另有说明, 否则类中所有方法的参数都不能为 null 虽然有些方法的参数是 URL 类型的, 但是这些方法实现通常不是以 HTTP 完成的 ; 同时这些资源也非 classpath 路径下的 下面两个函数都是根据资源的名称得到其绝对路径, 从函数里面可以看出,Resources 类中的 getresource 函数都是基于

More information

JavaIO.PDF

JavaIO.PDF O u t p u t S t ream j a v a. i o. O u t p u t S t r e a m w r i t e () f l u s h () c l o s e () public abstract void write(int b) throws IOException public void write(byte[] data) throws IOException

More information

3.1 num = 3 ch = 'C' 2

3.1 num = 3 ch = 'C' 2 Java 1 3.1 num = 3 ch = 'C' 2 final 3.1 final : final final double PI=3.1415926; 3 3.2 4 int 3.2 (long int) (int) (short int) (byte) short sum; // sum 5 3.2 Java int long num=32967359818l; C:\java\app3_2.java:6:

More information

untitled

untitled 1 Outline 數 料 數 數 列 亂數 練 數 數 數 來 數 數 來 數 料 利 料 來 數 A-Z a-z _ () 不 數 0-9 數 不 數 SCHOOL School school 數 讀 school_name schoolname 易 不 C# my name 7_eleven B&Q new C# (1) public protected private params override

More information

1.JasperReport ireport JasperReport ireport JDK JDK JDK JDK ant ant...6

1.JasperReport ireport JasperReport ireport JDK JDK JDK JDK ant ant...6 www.brainysoft.net 1.JasperReport ireport...4 1.1 JasperReport...4 1.2 ireport...4 2....4 2.1 JDK...4 2.1.1 JDK...4 2.1.2 JDK...5 2.1.3 JDK...5 2.2 ant...6 2.2.1 ant...6 2.2.2 ant...6 2.3 JasperReport...7

More information

雲端 Cloud Computing 技術指南 運算 應用 平台與架構 10/04/15 11:55:46 INFO 10/04/15 11:55:53 INFO 10/04/15 11:55:56 INFO 10/04/15 11:56:05 INFO 10/04/15 11:56:07 INFO

雲端 Cloud Computing 技術指南 運算 應用 平台與架構 10/04/15 11:55:46 INFO 10/04/15 11:55:53 INFO 10/04/15 11:55:56 INFO 10/04/15 11:56:05 INFO 10/04/15 11:56:07 INFO CHAPTER 使用 Hadoop 打造自己的雲 8 8.3 測試 Hadoop 雲端系統 4 Nodes Hadoop Map Reduce Hadoop WordCount 4 Nodes Hadoop Map/Reduce $HADOOP_HOME /home/ hadoop/hadoop-0.20.2 wordcount echo $ mkdir wordcount $ cd wordcount

More information

OOP with Java 通知 Project 4: 4 月 18 日晚 9 点 关于抄袭 没有分数

OOP with Java 通知 Project 4: 4 月 18 日晚 9 点 关于抄袭 没有分数 OOP with Java Yuanbin Wu cs@ecnu OOP with Java 通知 Project 4: 4 月 18 日晚 9 点 关于抄袭 没有分数 复习 类的复用 组合 (composition): has-a 关系 class MyType { public int i; public double d; public char c; public void set(double

More information

SDK 概要 使用 Maven 的用户可以从 Maven 库中搜索 "odps-sdk" 获取不同版本的 Java SDK: 包名 odps-sdk-core odps-sdk-commons odps-sdk-udf odps-sdk-mapred odps-sdk-graph 描述 ODPS 基

SDK 概要 使用 Maven 的用户可以从 Maven 库中搜索 odps-sdk 获取不同版本的 Java SDK: 包名 odps-sdk-core odps-sdk-commons odps-sdk-udf odps-sdk-mapred odps-sdk-graph 描述 ODPS 基 开放数据处理服务 ODPS SDK SDK 概要 使用 Maven 的用户可以从 Maven 库中搜索 "odps-sdk" 获取不同版本的 Java SDK: 包名 odps-sdk-core odps-sdk-commons odps-sdk-udf odps-sdk-mapred odps-sdk-graph 描述 ODPS 基础功能的主体接口, 搜索关键词 "odpssdk-core" 一些

More information

Chapter 9: Objects and Classes

Chapter 9: Objects and Classes Fortran Algol Pascal Modula-2 BCPL C Simula SmallTalk C++ Ada Java C# C Fortran 5.1 message A B 5.2 1 class Vehicle subclass Car object mycar public class Vehicle extends Object{ public int WheelNum

More information

chp6.ppt

chp6.ppt Java 软 件 设 计 基 础 6. 异 常 处 理 编 程 时 会 遇 到 如 下 三 种 错 误 : 语 法 错 误 (syntax error) 没 有 遵 循 语 言 的 规 则, 出 现 语 法 格 式 上 的 错 误, 可 被 编 译 器 发 现 并 易 于 纠 正 ; 逻 辑 错 误 (logic error) 即 我 们 常 说 的 bug, 意 指 编 写 的 代 码 在 执 行

More information

D C 93 2

D C 93 2 D9223468 3C 93 2 Java Java -- Java UML Java API UML MVC Eclipse API JavadocUML Omendo PSPPersonal Software Programming [6] 56 8 2587 56% Java 1 epaper(2005 ) Java C C (function) C (reusability) eat(chess1,

More information

EJB-Programming-4-cn.doc

EJB-Programming-4-cn.doc EJB (4) : (Entity Bean Value Object ) JBuilder EJB 2.x CMP EJB Relationships JBuilder EJB Test Client EJB EJB Seminar CMP Entity Beans Session Bean J2EE Session Façade Design Pattern Session Bean Session

More information

EJB-Programming-3.PDF

EJB-Programming-3.PDF :, JBuilder EJB 2.x CMP EJB Relationships JBuilder EJB Test Client EJB EJB Seminar CMP Entity Beans Value Object Design Pattern J2EE Design Patterns Value Object Value Object Factory J2EE EJB Test Client

More information

OOP with Java 通知 Project 4: 4 月 19 日晚 9 点

OOP with Java 通知 Project 4: 4 月 19 日晚 9 点 OOP with Java Yuanbin Wu cs@ecnu OOP with Java 通知 Project 4: 4 月 19 日晚 9 点 复习 类的复用 组合 (composition): has-a 关系 class MyType { public int i; public double d; public char c; public void set(double x) { d

More information

Fun Time (1) What happens in memory? 1 i n t i ; 2 s h o r t j ; 3 double k ; 4 char c = a ; 5 i = 3; j = 2; 6 k = i j ; H.-T. Lin (NTU CSIE) Referenc

Fun Time (1) What happens in memory? 1 i n t i ; 2 s h o r t j ; 3 double k ; 4 char c = a ; 5 i = 3; j = 2; 6 k = i j ; H.-T. Lin (NTU CSIE) Referenc References (Section 5.2) Hsuan-Tien Lin Deptartment of CSIE, NTU OOP Class, March 15-16, 2010 H.-T. Lin (NTU CSIE) References OOP 03/15-16/2010 0 / 22 Fun Time (1) What happens in memory? 1 i n t i ; 2

More information

Microsoft Word - Final Exam Review Packet.docx

Microsoft Word - Final Exam Review Packet.docx Do you know these words?... 3.1 3.5 Can you do the following?... Ask for and say the date. Use the adverbial of time correctly. Use Use to ask a tag question. Form a yes/no question with the verb / not

More information

Microsoft Word - 01.DOC

Microsoft Word - 01.DOC 第 1 章 JavaScript 简 介 JavaScript 是 NetScape 公 司 为 Navigator 浏 览 器 开 发 的, 是 写 在 HTML 文 件 中 的 一 种 脚 本 语 言, 能 实 现 网 页 内 容 的 交 互 显 示 当 用 户 在 客 户 端 显 示 该 网 页 时, 浏 览 器 就 会 执 行 JavaScript 程 序, 用 户 通 过 交 互 式 的

More information

KillTest 质量更高 服务更好 学习资料 半年免费更新服务

KillTest 质量更高 服务更好 学习资料   半年免费更新服务 KillTest 质量更高 服务更好 学习资料 http://www.killtest.cn 半年免费更新服务 Exam : 1Z0-854 Title : Java Standard Edition 5 Programmer Certified Professional Upgrade Exam Version : Demo 1 / 12 1.Given: 20. public class CreditCard

More information

软件工程文档编制

软件工程文档编制 实训抽象类 一 实训目标 掌握抽象类的定义 使用 掌握运行时多态 二 知识点 抽象类的语法格式如下 : public abstract class ClassName abstract void 方法名称 ( 参数 ); // 非抽象方法的实现代码 在使用抽象类时需要注意如下几点 : 1 抽象类不能被实例化, 实例化的工作应该交由它的子类来完成 2 抽象方法必须由子类来进行重写 3 只要包含一个抽象方法的抽象类,

More information

Java java.lang.math Java Java.util.Random : ArithmeticException int zero = 0; try { int i= 72 / zero ; }catch (ArithmeticException e ) { // } 0,

Java java.lang.math Java Java.util.Random : ArithmeticException int zero = 0; try { int i= 72 / zero ; }catch (ArithmeticException e ) { // } 0, http://debut.cis.nctu.edu.tw/~chi Java java.lang.math Java Java.util.Random : ArithmeticException int zero = 0; try { int i= 72 / zero ; }catch (ArithmeticException e ) { // } 0, : POSITIVE_INFINITY NEGATIVE_INFINITY

More information

使 用 Java 语 言 模 拟 保 险 箱 容 量 门 板 厚 度 箱 体 厚 度 属 性 锁 具 类 型 开 保 险 箱 关 保 险 箱 动 作 存 取 款

使 用 Java 语 言 模 拟 保 险 箱 容 量 门 板 厚 度 箱 体 厚 度 属 性 锁 具 类 型 开 保 险 箱 关 保 险 箱 动 作 存 取 款 JAVA 程 序 设 计 ( 肆 ) 徐 东 / 数 学 系 使 用 Java 语 言 模 拟 保 险 箱 容 量 门 板 厚 度 箱 体 厚 度 属 性 锁 具 类 型 开 保 险 箱 关 保 险 箱 动 作 存 取 款 使 用 Java class 代 表 保 险 箱 public class SaveBox 类 名 类 类 体 实 现 封 装 性 使 用 class SaveBox 代 表 保

More information

chp7.ppt

chp7.ppt Java 软件设计基础 7. Java 的基本可重用类 1.Java 可重用类的结构 Java 语言中将功能相关的可重用类组织成包, 可重用类的继承层次和包的组织呈树形结构 M L L L L L Java 可重用类按功能可划分为 : java.lang 是 Java 语言的核心包, 主要含有与语言相关的类 ; 提供如基本数据类型处理 基本数值函数 字符串处理 线程 异常处理等基本功能 ; 由解释程序自动加载,

More information

(TestFailure) JUnit Framework AssertionFailedError JUnit Composite TestSuite Test TestSuite run() run() JUnit

(TestFailure) JUnit Framework AssertionFailedError JUnit Composite TestSuite Test TestSuite run() run() JUnit Tomcat Web JUnit Cactus JUnit Java Cactus JUnit 26.1 JUnit Java JUnit JUnit Java JSP Servlet JUnit Java Erich Gamma Kent Beck xunit JUnit boolean JUnit Java JUnit Java JUnit Java 26.1.1 JUnit JUnit How

More information

科学计算的语言-FORTRAN95

科学计算的语言-FORTRAN95 科 学 计 算 的 语 言 -FORTRAN95 目 录 第 一 篇 闲 话 第 1 章 目 的 是 计 算 第 2 章 FORTRAN95 如 何 描 述 计 算 第 3 章 FORTRAN 的 编 译 系 统 第 二 篇 计 算 的 叙 述 第 4 章 FORTRAN95 语 言 的 形 貌 第 5 章 准 备 数 据 第 6 章 构 造 数 据 第 7 章 声 明 数 据 第 8 章 构 造

More information

javaexample-02.pdf

javaexample-02.pdf n e w. s t a t i c s t a t i c 3 1 3 2 p u b l i c p r i v a t e p r o t e c t e d j a v a. l a n g. O b j e c t O b j e c t Rect R e c t x 1 y 1 x 2 y 2 R e c t t o S t r i n g ( ) j a v a. l a n g. O

More information

FY.DOC

FY.DOC 高 职 高 专 21 世 纪 规 划 教 材 C++ 程 序 设 计 邓 振 杰 主 编 贾 振 华 孟 庆 敏 副 主 编 人 民 邮 电 出 版 社 内 容 提 要 本 书 系 统 地 介 绍 C++ 语 言 的 基 本 概 念 基 本 语 法 和 编 程 方 法, 深 入 浅 出 地 讲 述 C++ 语 言 面 向 对 象 的 重 要 特 征 : 类 和 对 象 抽 象 封 装 继 承 等 主

More information

OOP with Java 通知 Project 4: 5 月 2 日晚 9 点

OOP with Java 通知 Project 4: 5 月 2 日晚 9 点 OOP with Java Yuanbin Wu cs@ecnu OOP with Java 通知 Project 4: 5 月 2 日晚 9 点 复习 类的复用 组合 (composition): has-a 关系 class MyType { public int i; public double d; public char c; public void set(double x) { d =

More information

Microsoft Word - sy09_实验09_字符串和文本IO.docx

Microsoft Word - sy09_实验09_字符串和文本IO.docx 面向对象程序设计 (Java) 课程实验 第 9 章字符串和文本 I/O 9.1 找出回文串检测一个字符串是否是回文串 : 从前向后和从后向前读都是同一个字符串的字符串 public class CheckPalindrome { // Create a Scanner Scanner input = new Scanner(System.in); // Prompt the user to enter

More information

KillTest 质量更高 服务更好 学习资料 半年免费更新服务

KillTest 质量更高 服务更好 学习资料   半年免费更新服务 KillTest 质量更高 服务更好 学习资料 http://www.killtest.cn 半年免费更新服务 Exam : 310-055Big5 Title : Sun Certified Programmer for the Java 2 Platform.SE 5.0 Version : Demo 1 / 22 1. 11. public static void parse(string str)

More information

Bus Hound 5

Bus Hound 5 Bus Hound 5.0 ( 1.0) 21IC 2007 7 BusHound perisoft PC hound Bus Hound 6.0 5.0 5.0 Bus Hound, IDE SCSI USB 1394 DVD Windows9X,WindowsMe,NT4.0,2000,2003,XP XP IRP Html ZIP SCSI sense USB Bus Hound 1 Bus

More information

epub83-1

epub83-1 C++Builder 1 C + + B u i l d e r C + + B u i l d e r C + + B u i l d e r C + + B u i l d e r 1.1 1.1.1 1-1 1. 1-1 1 2. 1-1 2 A c c e s s P a r a d o x Visual FoxPro 3. / C / S 2 C + + B u i l d e r / C

More information

无类继承.key

无类继承.key 无类继承 JavaScript 面向对象的根基 周爱 民 / aimingoo aiming@gmail.com https://aimingoo.github.io https://github.com/aimingoo rand = new Person("Rand McKinnon",... https://docs.oracle.com/cd/e19957-01/816-6408-10/object.htm#1193255

More information

詞 彙 表 編 號 詞 彙 描 述 1 預 約 人 資 料 中 文 姓 名 英 文 姓 名 身 份 證 字 號 預 約 人 電 話 性 別 2 付 款 資 料 信 用 卡 別 信 用 卡 號 信 用 卡 有 效 日 期 3 住 房 條 件 入 住 日 期 退 房 日 期 人 數 房 間 數 量 入

詞 彙 表 編 號 詞 彙 描 述 1 預 約 人 資 料 中 文 姓 名 英 文 姓 名 身 份 證 字 號 預 約 人 電 話 性 別 2 付 款 資 料 信 用 卡 別 信 用 卡 號 信 用 卡 有 效 日 期 3 住 房 條 件 入 住 日 期 退 房 日 期 人 數 房 間 數 量 入 100 年 特 種 考 試 地 方 政 府 公 務 人 員 考 試 試 題 等 別 : 三 等 考 試 類 科 : 資 訊 處 理 科 目 : 系 統 分 析 與 設 計 一 請 參 考 下 列 旅 館 管 理 系 統 的 使 用 案 例 圖 (Use Case Diagram) 撰 寫 預 約 房 間 的 使 用 案 例 規 格 書 (Use Case Specification), 繪 出 入

More information

1 4 1.1 4 1.2..4 2..4 2.1..4 3.4 3.1 Java.5 3.1.1..5 3.1.2 5 3.1.3 6 4.6 4.1 6 4.2.6 5 7 5.1..8 5.1.1 8 5.1.2..8 5.1.3..8 5.1.4..9 5.2..9 6.10 6.1.10

1 4 1.1 4 1.2..4 2..4 2.1..4 3.4 3.1 Java.5 3.1.1..5 3.1.2 5 3.1.3 6 4.6 4.1 6 4.2.6 5 7 5.1..8 5.1.1 8 5.1.2..8 5.1.3..8 5.1.4..9 5.2..9 6.10 6.1.10 Java V1.0.1 2007 4 10 1 4 1.1 4 1.2..4 2..4 2.1..4 3.4 3.1 Java.5 3.1.1..5 3.1.2 5 3.1.3 6 4.6 4.1 6 4.2.6 5 7 5.1..8 5.1.1 8 5.1.2..8 5.1.3..8 5.1.4..9 5.2..9 6.10 6.1.10 6.2.10 6.3..10 6.4 11 7.12 7.1

More information

拦截器(Interceptor)的学习

拦截器(Interceptor)的学习 二 拦截器 (Interceptor) 的学习 拦截器可以监听程序的一个或所有方法 拦截器对方法调用流提供了细粒度控制 可以在无状态会话 bean 有状态会话 bean 和消息驱动 bean 上使用它们 拦截器可以是同一 bean 类中的方法或是一个外部类 下面介绍如何在 Session Bean 类中使用外部拦截器类 @Interceptors 注释指定一个或多个在外部类中定义的拦截器 下面拦截器

More information

untitled

untitled 4.1AOP AOP Aspect-oriented programming AOP 來說 AOP 令 理 Cross-cutting concerns Aspect Weave 理 Spring AOP 來 AOP 念 4.1.1 理 AOP AOP 見 例 來 例 錄 Logging 錄 便 來 例 行 留 錄 import java.util.logging.*; public class HelloSpeaker

More information

OOP with Java 通知 Project 3: 3 月 29 日晚 9 点 4 月 1 日上课

OOP with Java 通知 Project 3: 3 月 29 日晚 9 点 4 月 1 日上课 OOP with Java Yuanbin Wu cs@ecnu OOP with Java 通知 Project 3: 3 月 29 日晚 9 点 4 月 1 日上课 复习 Java 包 创建包 : package 语句, 包结构与目录结构一致 使用包 : import restaurant/ - people/ - Cook.class - Waiter.class - tools/ - Fork.class

More information

《计算概论》课程 第十九讲 C 程序设计语言应用

《计算概论》课程 第十九讲  C 程序设计语言应用 Java 高级技术 课程 Java 语言的高级特性 李戈 北京大学信息科学技术学院软件研究所 2009 年 4 月 11 日 输入 / 输出流 输入 / 输出流 为输入 / 输出数据,Java 程序与数据的发送者或接收者要建立一个数据通道, 这个通道被抽象为流 (stream); Java 语言本身不包含输入 / 输出语句, 而是通过 Java API 提供的程序包 java.io 完成的 ; 输入

More information

Fuzzy Highlight.ppt

Fuzzy Highlight.ppt Fuzzy Highlight high light Openfind O(kn) n k O(nm) m Knuth O(n) m Knuth Unix grep regular expression exact match Yahoo agrep fuzzy match Gais agrep Openfind gais exact match fuzzy match fuzzy match O(kn)

More information

使用MapReduce读取XML文件

使用MapReduce读取XML文件 使用 MapReduce 读取 XML 文件 XML( 可扩展标记语言, 英语 :extensible Markup Language, 简称 : XML) 是一种标记语言, 也是行业标准数据交换交换格式, 它很适合在系统之间进行数据存储和交换 ( 话说 Hadoop H ive 等的配置文件就是 XML 格式的 ) 本文将介绍如何使用 MapReduce 来读取 XML 文件 但是 Had oop

More information

Microsoft Word - template.doc

Microsoft Word - template.doc HGC efax Service User Guide I. Getting Started Page 1 II. Fax Forward Page 2 4 III. Web Viewing Page 5 7 IV. General Management Page 8 12 V. Help Desk Page 13 VI. Logout Page 13 Page 0 I. Getting Started

More information

9, : Java 19., [4 ]. 3 Apla2Java Apla PAR,Apla2Java Apla Java.,Apla,,, 1. 1 Apla Apla A[J ] Get elem (set A) A J A B Intersection(set A,set B) A B A B

9, : Java 19., [4 ]. 3 Apla2Java Apla PAR,Apla2Java Apla Java.,Apla,,, 1. 1 Apla Apla A[J ] Get elem (set A) A J A B Intersection(set A,set B) A B A B 25 9 2008 9 M ICROEL ECTRON ICS & COMPU TER Vol. 25 No. 9 September 2008 J ava 1,2, 1,2, 1,2 (1, 330022 ; 2, 330022) :,. Apla - Java,,.. : PAR ;Apla - Java ; ;CMP ; : TP311 : A : 1000-7180 (2008) 09-0018

More information

2009年9月全国计算机等级考试二级Java真题及答案

2009年9月全国计算机等级考试二级Java真题及答案 2009 年 9 月 全 国 计 算 机 等 级 考 试 二 级 Java 真 题 及 答 案 [ 录 入 者 :NCRE100 时 间 :2009-10-08 19:41:34 作 者 : 来 源 :NCRE100.com 浏 览 :1421 次 ] 2009 年 9 月 全 国 计 算 机 等 级 考 试 二 级 笔 试 试 卷 Java 语 言 程 序 设 计 ( 考 试 时 间 90 分 钟,

More information

帝国CMS下在PHP文件中调用数据库类执行SQL语句实例

帝国CMS下在PHP文件中调用数据库类执行SQL语句实例 帝国 CMS 下在 PHP 文件中调用数据库类执行 SQL 语句实例 这篇文章主要介绍了帝国 CMS 下在 PHP 文件中调用数据库类执行 SQL 语句实例, 本文还详细介绍了帝国 CMS 数据库类中的一些常用方法, 需要的朋友可以参考下 例 1: 连接 MYSQL 数据库例子 (a.php)

More information

untitled

untitled 1 Outline 料 類 說 Tang, Shih-Hsuan 2006/07/26 ~ 2006/09/02 六 PM 7:00 ~ 9:30 聯 ives.net@gmail.com www.csie.ntu.edu.tw/~r93057/aspnet134 度 C# 力 度 C# Web SQL 料 DataGrid DataList 參 ASP.NET 1.0 C# 例 ASP.NET 立

More information

x MapReduce A Italic URL Constant width Constant width bold Constant width italic 這個圖示代表提示或建議 這個圖示代表一般註解

x MapReduce A Italic URL Constant width Constant width bold Constant width italic 這個圖示代表提示或建議 這個圖示代表一般註解 Java R Python Java Java Java x MapReduce A Italic URL Constant width Constant width bold Constant width italic 這個圖示代表提示或建議 這個圖示代表一般註解 第一章 I/O double[][] int[] String[] List 2 Map JavaScript Object Notation

More information

Chapter 9: Objects and Classes

Chapter 9: Objects and Classes Java application Java main applet Web applet Runnable Thread CPU Thread 1 Thread 2 Thread 3 CUP Thread 1 Thread 2 Thread 3 ,,. (new) Thread (runnable) start( ) CPU (running) run ( ) blocked CPU sleep(

More information

Python a p p l e b e a r c Fruit Animal a p p l e b e a r c 2-2

Python a p p l e b e a r c Fruit Animal a p p l e b e a r c 2-2 Chapter 02 變數與運算式 2.1 2.1.1 2.1.2 2.1.3 2.1.4 2.2 2.2.1 2.2.2 2.2.3 type 2.2.4 2.3 2.3.1 print 2.3.2 input 2.4 2.4.1 2.4.2 2.4.3 2.4.4 2.4.5 + 2.4.6 Python Python 2.1 2.1.1 a p p l e b e a r c 65438790

More information

目 录 实 验 一 : 熟 悉 Java 开 发 环 境... 1 实 验 二 : 类 与 面 向 对 象... 7 实 验 三 : 继 承 和 多 态... 13 实 验 四 : 异 常 处 理... 18 实 验 五 : 流 文 件 及 基 于 文 本 的 应 用... 23

目 录 实 验 一 : 熟 悉 Java 开 发 环 境... 1 实 验 二 : 类 与 面 向 对 象... 7 实 验 三 : 继 承 和 多 态... 13 实 验 四 : 异 常 处 理... 18 实 验 五 : 流 文 件 及 基 于 文 本 的 应 用... 23 Java 程 序 设 计 实 验 指 导 书 商 丘 学 院 计 算 机 科 学 与 技 术 学 院 张 艳 晓 目 录 实 验 一 : 熟 悉 Java 开 发 环 境... 1 实 验 二 : 类 与 面 向 对 象... 7 实 验 三 : 继 承 和 多 态... 13 实 验 四 : 异 常 处 理... 18 实 验 五 : 流 文 件 及 基 于 文 本 的 应 用... 23 实 验

More information

Java 1 Java String Date

Java 1 Java String Date JAVA SCJP Java 1 Java String Date 1Java 01 Java Java 1995 Java Java 21 Java Java 5 1-1 Java Java 1990 12 Patrick Naughton C++ C (Application Programming Interface API Library) Patrick Naughton NeXT Stealth

More information

lnag_ch_v2.01.doc

lnag_ch_v2.01.doc 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. % Any line starting with "%" is a comment. % "\" (backslash) is a special Latex character which introduces a Latex %

More information

Mac Java import com.apple.mrj.*;... public class MyFirstApp extends JFrame implements ActionListener, MRJAboutHandler, MRJQuitHandler {... public MyFirstApp() {... MRJApplicationUtils.registerAboutHandler(this);

More information

untitled

untitled 3 C++ 3.1 3.2 3.3 3.4 new delete 3.5 this 3.6 3.7 3.1 3.1 class struct union struct union C class C++ C++ 3.1 3.1 #include struct STRING { typedef char *CHARPTR; // CHARPTR s; // int strlen(

More information

Linux服务器构建与运维管理

Linux服务器构建与运维管理 1 Linux 服务器构建与运维管理 第 2 章 :Linux 基本命令 阮晓龙 13938213680 / rxl@hactcm.edu.cn http://linux.xg.hactcm.edu.cn http://www.51xueweb.cn 河南中医药大学管理科学与工程学科 2018.3 2 提纲 目录与文件的操作 mkdir touch mv cp rm rmdir file tree

More information

《大话设计模式》第一章

《大话设计模式》第一章 第 1 章 代 码 无 错 就 是 优? 简 单 工 厂 模 式 1.1 面 试 受 挫 小 菜 今 年 计 算 机 专 业 大 四 了, 学 了 不 少 软 件 开 发 方 面 的 东 西, 也 学 着 编 了 些 小 程 序, 踌 躇 满 志, 一 心 要 找 一 个 好 单 位 当 投 递 了 无 数 份 简 历 后, 终 于 收 到 了 一 个 单 位 的 面 试 通 知, 小 菜 欣 喜

More information

2015 Chinese FL Written examination

2015 Chinese FL Written examination Victorian Certificate of Education 2015 SUPERVISOR TO ATTACH PROCESSING LABEL HERE Letter STUDENT NUMBER CHINESE FIRST LANGUAGE Written examination Monday 16 November 2015 Reading time: 11.45 am to 12.00

More information

2009年3月全国计算机等级考试二级Java语言程序设计笔试试题

2009年3月全国计算机等级考试二级Java语言程序设计笔试试题 2009 年 3 月 全 国 计 算 机 等 级 考 试 笔 试 试 卷 二 级 Java 语 言 程 序 设 计 ( 考 试 时 间 90 分 钟, 满 分 100 分 ) 一 选 择 题 ( 每 题 2 分, 共 70 分 ) 下 列 各 题 A) B) C) D) 四 个 选 项 中, 只 有 一 个 选 项 是 正 确 的 请 将 正 确 选 项 填 涂 在 答 题 卡 相 应 位 置 上,

More information

untitled

untitled 2006 6 Geoframe Geoframe 4.0.3 Geoframe 1.2 1 Project Manager Project Management Create a new project Create a new project ( ) OK storage setting OK (Create charisma project extension) NO OK 2 Edit project

More information

内 容 简 介 本 书 是 一 本 关 于 语 言 程 序 设 计 的 教 材, 涵 盖 了 语 言 的 基 本 语 法 和 编 程 技 术, 其 中 包 含 了 作 者 对 语 言 多 年 开 发 经 验 的 总 结, 目 的 是 让 初 学 的 读 者 感 受 到 语 言 的 魅 力, 并 掌

内 容 简 介 本 书 是 一 本 关 于 语 言 程 序 设 计 的 教 材, 涵 盖 了 语 言 的 基 本 语 法 和 编 程 技 术, 其 中 包 含 了 作 者 对 语 言 多 年 开 发 经 验 的 总 结, 目 的 是 让 初 学 的 读 者 感 受 到 语 言 的 魅 力, 并 掌 语 言 程 序 设 计 郑 莉 胡 家 威 编 著 清 华 大 学 逸 夫 图 书 馆 北 京 内 容 简 介 本 书 是 一 本 关 于 语 言 程 序 设 计 的 教 材, 涵 盖 了 语 言 的 基 本 语 法 和 编 程 技 术, 其 中 包 含 了 作 者 对 语 言 多 年 开 发 经 验 的 总 结, 目 的 是 让 初 学 的 读 者 感 受 到 语 言 的 魅 力, 并 掌 握 语

More information

AN INTRODUCTION TO PHYSICAL COMPUTING USING ARDUINO, GRASSHOPPER, AND FIREFLY (CHINESE EDITION ) INTERACTIVE PROTOTYPING

AN INTRODUCTION TO PHYSICAL COMPUTING USING ARDUINO, GRASSHOPPER, AND FIREFLY (CHINESE EDITION ) INTERACTIVE PROTOTYPING AN INTRODUCTION TO PHYSICAL COMPUTING USING ARDUINO, GRASSHOPPER, AND FIREFLY (CHINESE EDITION ) INTERACTIVE PROTOTYPING 前言 - Andrew Payne 目录 1 2 Firefly Basics 3 COMPONENT TOOLBOX 目录 4 RESOURCES 致谢

More information

概述

概述 OPC Version 1.6 build 0910 KOSRDK Knight OPC Server Rapid Development Toolkits Knight Workgroup, eehoo Technology 2002-9 OPC 1...4 2 API...5 2.1...5 2.2...5 2.2.1 KOS_Init...5 2.2.2 KOS_InitB...5 2.2.3

More information

《计算概论》课程 第十九讲 C 程序设计语言应用

《计算概论》课程 第十九讲  C 程序设计语言应用 计算概论 A 程序设计部分 字符数组与字符串 李戈 北京大学信息科学技术学院软件研究所 lige@sei.pku.edu.cn 字符数组的定义 #include int main() char a[10] = 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j' ; for (int i = 0; i < 10; i++) cout

More information

全国计算机技术与软件专业技术资格(水平)考试

全国计算机技术与软件专业技术资格(水平)考试 全 国 计 算 机 技 术 与 软 件 专 业 技 术 资 格 ( 水 平 ) 考 试 2008 年 上 半 年 程 序 员 下 午 试 卷 ( 考 试 时 间 14:00~16:30 共 150 分 钟 ) 试 题 一 ( 共 15 分 ) 阅 读 以 下 说 明 和 流 程 图, 填 补 流 程 图 中 的 空 缺 (1)~(9), 将 解 答 填 入 答 题 纸 的 对 应 栏 内 [ 说 明

More information

untitled

untitled 1 MSDN Library MSDN Library 量 例 參 列 [ 說 ] [] [ 索 ] [] 來 MSDN Library 了 類 類 利 F1 http://msdn.microsoft.com/library/ http://msdn.microsoft.com/library/cht/ Object object 參 類 都 object 參 object Boxing 參 boxing

More information

1: public class MyOutputStream implements AutoCloseable { 3: public void close() throws IOException { 4: throw new IOException(); 5: } 6:

1: public class MyOutputStream implements AutoCloseable { 3: public void close() throws IOException { 4: throw new IOException(); 5: } 6: Chapter 15. Suppressed Exception CH14 Finally Block Java SE 7 try-with-resources JVM cleanup try-with-resources JVM cleanup cleanup Java SE 7 Throwable getsuppressed Throwable[] getsuppressed() Suppressed

More information

Guide to Install SATA Hard Disks

Guide to Install SATA Hard Disks SATA RAID 1. SATA. 2 1.1 SATA. 2 1.2 SATA 2 2. RAID (RAID 0 / RAID 1 / JBOD).. 4 2.1 RAID. 4 2.2 RAID 5 2.3 RAID 0 6 2.4 RAID 1.. 10 2.5 JBOD.. 16 3. Windows 2000 / Windows XP 20 1. SATA 1.1 SATA Serial

More information

untitled

untitled 1 Outline ArrayList 類 列類 串類 類 類 例 理 MSDN Library MSDN Library 量 例 參 列 [ 說 ] [] [ 索 ] [] 來 MSDN Library 了 類 類 利 F1 http://msdn.microsoft.com/library/ http://msdn.microsoft.com/library/cht/ Object object

More information

<4D6963726F736F667420506F776572506F696E74202D20332D322E432B2BC3E6CFF2B6D4CFF3B3CCD0F2C9E8BCC6A1AAD6D8D4D8A1A2BCCCB3D0A1A2B6E0CCACBACDBEDBBACF2E707074>

<4D6963726F736F667420506F776572506F696E74202D20332D322E432B2BC3E6CFF2B6D4CFF3B3CCD0F2C9E8BCC6A1AAD6D8D4D8A1A2BCCCB3D0A1A2B6E0CCACBACDBEDBBACF2E707074> 程 序 设 计 实 习 INFO130048 3-2.C++ 面 向 对 象 程 序 设 计 重 载 继 承 多 态 和 聚 合 复 旦 大 学 计 算 机 科 学 与 工 程 系 彭 鑫 pengxin@fudan.edu.cn 内 容 摘 要 方 法 重 载 类 的 继 承 对 象 引 用 和 拷 贝 构 造 函 数 虚 函 数 和 多 态 性 类 的 聚 集 复 旦 大 学 计 算 机 科 学

More information

Microsoft PowerPoint - string_kruse [兼容模式]

Microsoft PowerPoint - string_kruse [兼容模式] Strings Strings in C not encapsulated Every C-string has type char *. Hence, a C-string references an address in memory, the first of a contiguous set of bytes that store the characters making up the string.

More information

ebook39-6

ebook39-6 6 first-in-first-out, FIFO L i n e a r L i s t 3-1 C h a i n 3-8 5. 5. 3 F I F O L I F O 5. 5. 6 5. 5. 6.1 [ ] q u e n e ( r e a r ) ( f r o n t 6-1a A 6-1b 6-1b D C D 6-1c a) b) c) 6-1 F I F O L I F ADT

More information

K7VT2_QIG_v3

K7VT2_QIG_v3 ............ 1 2 3 4 5 [R] : Enter Raid setup utility 6 Press[A]keytocreateRAID RAID Type: JBOD RAID 0 RAID 1: 2 7 RAID 0 Auto Create Manual Create: 2 RAID 0 Block Size: 16K 32K

More information

JAVA 单元 2.1 四则运算机 ( 一 ) 单元教学进度设计 教学环节 教学内容 教师学生活动活动 反馈 反馈课前作业完成情况 反馈加分 1. 下面哪些是合法的变量名? ( ) A.2variable 答案 :DEG B..variable2 解答 : C.._whatavariable A:/

JAVA 单元 2.1 四则运算机 ( 一 ) 单元教学进度设计 教学环节 教学内容 教师学生活动活动 反馈 反馈课前作业完成情况 反馈加分 1. 下面哪些是合法的变量名? ( ) A.2variable 答案 :DEG B..variable2 解答 : C.._whatavariable A:/ 单元 2.1 四则运算机 ( 一 ) 单元教学进度设计 教学环节 教学内容 教师学生活动活动 反馈 反馈课前作业完成情况 反馈加分 1. 下面哪些是合法的变量名? ( ) A.2variable 答案 :DEG B..variable2 解答 : C.._whatavariable A:// 不能以数字开头 D._3_ B:// 不能用点和空格 提问 抢答 E.$anothervar C: // 不能用点和空格

More information

文件

文件 CH10 文件 1 文件的概念 一 文件分类 二 文件的组织结构 : ASCII 码文件 ( 文本文件 ) 二进制文件 文件是二进制代码的, 则文件就是字节流 文件是 ASCII 码的, 则文件就是字符流, 也是字节流 1 如 : 对于整型变量 x, 其值为 32767 若以文本方式存放, 则共有 5 个字符, 内容为 : 00110011 00110010 00110111 00110110 00110111

More information

Swing-02.pdf

Swing-02.pdf 2 J B u t t o n J T e x t F i e l d J L i s t B u t t o n T e x t F i e l d L i s t J F r a m e 21 2 2 Swing C a n v a s C o m p o n e n t J B u t t o n AWT // ToolbarFrame1.java // java.awt.button //

More information

OOP with Java 通知 Project 2 提交时间 : 3 月 14 日晚 9 点 另一名助教 : 王桢 学习使用文本编辑器 学习使用 cmd: Power shell 阅读参考资料

OOP with Java 通知 Project 2 提交时间 : 3 月 14 日晚 9 点 另一名助教 : 王桢   学习使用文本编辑器 学习使用 cmd: Power shell 阅读参考资料 OOP with Java Yuanbin Wu cs@ecnu OOP with Java 通知 Project 2 提交时间 : 3 月 14 日晚 9 点 另一名助教 : 王桢 Email: 51141201063@ecnu.cn 学习使用文本编辑器 学习使用 cmd: Power shell 阅读参考资料 OOP with Java Java 类型 引用 不可变类型 对象存储位置 作用域 OOP

More information

JAVA String常用APi

JAVA String常用APi JAVA String 常 用API 2015 年 5 月13 日 星 期 三 ------------------------------------------ String 类 的 特 点 : 字 符 串 对 象 一 旦 被 初 始 化 就 不 会 被 改 变 abc 存 储 在 字 符 串 常 量 池 中 Java 的 核 心 类 包 是 java.lang eclipse:ctrl+ 方

More information

1 Framework.NET Framework Microsoft Windows.NET Framework.NET Framework NOTE.NET NET Framework.NET Framework 2.0 ( 3 ).NET Framework 2.0.NET F

1 Framework.NET Framework Microsoft Windows.NET Framework.NET Framework NOTE.NET NET Framework.NET Framework 2.0 ( 3 ).NET Framework 2.0.NET F 1 Framework.NET Framework Microsoft Windows.NET Framework.NET Framework NOTE.NET 2.0 2.0.NET Framework.NET Framework 2.0 ( 3).NET Framework 2.0.NET Framework ( System ) o o o o o o Boxing UnBoxing() o

More information

untitled

untitled 1 行 行 行 行.NET 行 行 類 來 行 行 Thread 類 行 System.Threading 來 類 Thread 類 (1) public Thread(ThreadStart start ); Name 行 IsAlive 行 行狀 Start 行 行 Suspend 行 Resume 行 行 Thread 類 (2) Sleep 行 CurrentThread 行 ThreadStart

More information

Microsoft Word - linux命令及建议.doc

Microsoft Word - linux命令及建议.doc Linux 操 作 系 统 命 令 集 1 基 本 命 令 查 看 系 统 信 息 : uname -a 修 改 密 码 : passwd 退 出 : logout(exit) 获 取 帮 助 : man commands 2 文 件 和 目 录 命 令 显 示 当 前 工 作 目 录 : pwd 改 变 所 在 目 录 : cd cd - 切 换 到 上 一 次 使 用 的 目 录 cd 切 换

More information

Microsoft Word - ch04三校.doc

Microsoft Word - ch04三校.doc 4-1 4-1-1 (Object) (State) (Behavior) ( ) ( ) ( method) ( properties) ( functions) 4-2 4-1-2 (Message) ( ) ( ) ( ) A B A ( ) ( ) ( YourCar) ( changegear) ( lowergear) 4-1-3 (Class) (Blueprint) 4-3 changegear

More information

Learning Java

Learning Java Java Introduction to Java Programming (Third Edition) Prentice-Hall,Inc. Y.Daniel Liang 2001 Java 2002.2 Java2 2001.10 Java2 Philip Heller & Simon Roberts 1999.4 Java2 2001.3 Java2 21 2002.4 Java UML 2002.10

More information

Microsoft Word - JAVA Programming Language Homework VI_ans.doc

Microsoft Word - JAVA Programming Language Homework VI_ans.doc JAVA Programming Language Homework VI: Threads & I/O ID: Name: 1. When comparing java.io.bufferedwriter to java.io.filewriter, which capability exists as a method in only one of the two? A. Closing the

More information

《面向对象程序设计A》课程教学大纲Ⅱ4

《面向对象程序设计A》课程教学大纲Ⅱ4 Java 程 序 设 计 课 程 教 学 大 纲 Ⅱ5 课 程 代 码 : 课 程 名 称 :Java 程 序 设 计 Java Programming 学 分 :5 总 学 时 :80 ( 其 中 : 理 论 学 时 :48 实 验 ( 上 机 ) 学 时 :32) 先 修 课 程 : 2106010190 大 学 计 算 机 信 息 技 术 基 础 适 用 对 象 : 本 二 工 科 非 计 算

More information

6-1 Table Column Data Type Row Record 1. DBMS 2. DBMS MySQL Microsoft Access SQL Server Oracle 3. ODBC SQL 1. Structured Query Language 2. IBM

6-1 Table Column Data Type Row Record 1. DBMS 2. DBMS MySQL Microsoft Access SQL Server Oracle 3. ODBC SQL 1. Structured Query Language 2. IBM CHAPTER 6 SQL SQL SQL 6-1 Table Column Data Type Row Record 1. DBMS 2. DBMS MySQL Microsoft Access SQL Server Oracle 3. ODBC SQL 1. Structured Query Language 2. IBM 3. 1986 10 ANSI SQL ANSI X3. 135-1986

More information

C H A P T E R 7 Windows Vista Windows Vista Windows Vista FAT16 FAT32 NTFS NTFS New Technology File System NTFS

C H A P T E R 7 Windows Vista Windows Vista Windows Vista FAT16 FAT32 NTFS NTFS New Technology File System NTFS C H P T E R 7 Windows Vista Windows Vista Windows VistaFT16 FT32NTFS NTFSNew Technology File System NTFS 247 6 7-1 Windows VistaTransactional NTFS TxFTxF Windows Vista MicrosoftTxF CIDatomicity - Consistency

More information

基于ECO的UML模型驱动的数据库应用开发1.doc

基于ECO的UML模型驱动的数据库应用开发1.doc ECO UML () Object RDBMS Mapping.Net Framework Java C# RAD DataSetOleDbConnection DataGrod RAD Client/Server RAD RAD DataReader["Spell"].ToString() AObj.XXX bug sql UML OR Mapping RAD Lazy load round trip

More information

LEETCODE leetcode.com 一 个 在 线 编 程 网 站, 收 集 了 IT 公 司 的 面 试 题, 包 括 算 法, 数 据 库 和 shell 算 法 题 支 持 多 种 语 言, 包 括 C, C++, Java, Python 等 2015 年 3 月 份 加 入 了 R

LEETCODE leetcode.com 一 个 在 线 编 程 网 站, 收 集 了 IT 公 司 的 面 试 题, 包 括 算 法, 数 据 库 和 shell 算 法 题 支 持 多 种 语 言, 包 括 C, C++, Java, Python 等 2015 年 3 月 份 加 入 了 R 用 RUBY 解 LEETCODE 算 法 题 RUBY CONF CHINA 2015 By @quakewang LEETCODE leetcode.com 一 个 在 线 编 程 网 站, 收 集 了 IT 公 司 的 面 试 题, 包 括 算 法, 数 据 库 和 shell 算 法 题 支 持 多 种 语 言, 包 括 C, C++, Java, Python 等 2015 年 3 月 份

More information

<4D6963726F736F667420576F7264202D20BAF4BADEA457BDD2B1D0A7F75F4A415641B57BA6A1B2D52E646F63>

<4D6963726F736F667420576F7264202D20BAF4BADEA457BDD2B1D0A7F75F4A415641B57BA6A1B2D52E646F63> 電 腦 網 路 與 程 式 課 程 JAVA 物 件 導 向 程 式 設 計 JAVA 程 式 組 教 材 授 課 人 員 : 黃 怡 傑 目 錄 Ch1. 學 習 JAVA 的 第 一 堂 課 程 式 的 邏 輯 1.1 coding 的 習 慣 1.2 開 始 學 習 JAVA 前 的 準 備 1.3 第 一 個 JAVA 程 式 1.4 資 料 型 別 1.5 運 算 子 1.6 迴 圈 1.7

More information

Microsoft PowerPoint - ch7_1 DA class

Microsoft PowerPoint - ch7_1 DA class Quiz 1. Describe the similarities and differences of Tester class and GUI class 2. What is the function of GUI class? 3. What is the function of PD(problem domain) class? 4. How does a GUI class interact

More information

4. 每 组 学 生 将 写 有 习 语 和 含 义 的 两 组 卡 片 分 别 洗 牌, 将 顺 序 打 乱, 然 后 将 两 组 卡 片 反 面 朝 上 置 于 课 桌 上 5. 学 生 依 次 从 两 组 卡 片 中 各 抽 取 一 张, 展 示 给 小 组 成 员, 并 大 声 朗 读 卡

4. 每 组 学 生 将 写 有 习 语 和 含 义 的 两 组 卡 片 分 别 洗 牌, 将 顺 序 打 乱, 然 后 将 两 组 卡 片 反 面 朝 上 置 于 课 桌 上 5. 学 生 依 次 从 两 组 卡 片 中 各 抽 取 一 张, 展 示 给 小 组 成 员, 并 大 声 朗 读 卡 Tips of the Week 课 堂 上 的 英 语 习 语 教 学 ( 二 ) 2015-04-19 吴 倩 MarriottCHEI 大 家 好! 欢 迎 来 到 Tips of the Week! 这 周 我 想 和 老 师 们 分 享 另 外 两 个 课 堂 上 可 以 开 展 的 英 语 习 语 教 学 活 动 其 中 一 个 活 动 是 一 个 充 满 趣 味 的 游 戏, 另 外

More information

java2d-4.PDF

java2d-4.PDF 75 7 6 G r a d i e n t P a i n t B a s i c S t r o k e s e t P a i n t ( ) s e t S t o r k e ( ) import java.awt.*; import java.awt.geom.*; public class PaintingAndStroking extends ApplicationFrame { public

More information

JBuilder Weblogic

JBuilder Weblogic JUnit ( bliu76@yeah.net) < >6 JUnit Java Erich Gamma Kent Beck JUnit JUnit 1 JUnit 1.1 JUnit JUnit java XUnit JUnit 1.2 JUnit JUnit Erich Gamma Kent Beck Erich Gamma Kent Beck XP Extreme Programming CRC

More information

OOP with Java 通知 Project 3 提交时间 3 月 29 日晚 9 点 Piazza Project 2 投票

OOP with Java 通知 Project 3 提交时间 3 月 29 日晚 9 点 Piazza Project 2 投票 OOP with Java Yuanbin Wu cs@ecnu OOP with Java 通知 Project 3 提交时间 3 月 29 日晚 9 点 Piazza Project 2 投票 复习 创建对象 构造函数 函数重载 : 函数 = 函数名 + 参数列表 public class MyType { int i; double d; char c; void set(double x)

More information