黑马程序员-笔记-10-IO其他

来源:互联网 发布:国家数据统计局 编辑:程序博客网 时间:2024/06/10 00:14

---------------------- ASP.Net+Android+IOS开发.Net培训、期待与您交流! ----------------------

java装饰类:对类的功能进行加强,同时避免了继承所带来的代码臃肿 降低了类之间的耦合性。
     java中,带缓冲作用的流,其本质就是装饰类,它本身需要一个流支持。 
//装饰类,实现java中LineNumberReader同样的功能。

class MyLineReader {     private Reader reader; //装饰类需要从外部传入一个需要加强的类。    int limitNumber = 0; //设置,需要从哪一行开始读。    private int lineNumber = 0; //当前流读到了哪一行。     //构造方法,用来接收外部须加强的类。    MyLineReader(Reader reader) {       this.reader = reader;    }     //方法:设置从哪一行开始读。    public void setLineNumber(int limitNumber) {       this.limitNumber = limitNumber;    }     //方法,读取一行。    public String readLineNum() throws IOException {       //按要求,应该从limitNumber行读起,所以,要先将前limitNumber-1行读完,这些并不使用。       if (lineNumber < limitNumber - 1) {           for (int i = 1; i < limitNumber; i++) {              readLine();           }       }    //如果当前行数已经从limitNumber以后读起,则没有必要。       return readLine();    }    public String readLine() throws IOException {       lineNumber++;//记录当前的行数。每次读取增加1       StringBuffer sbf = new StringBuffer();       int i = 0;       //循环读入,当读到回车时,返回改行。       while ((i = reader.read()) != -1) {           if ((char) i == '\r')              continue;           if ((char) i == '\n')              break;           sbf.append((char) i);       }       if (sbf.length() > 0)           return sbf.toString();       if(i==-1)       return null;       else//因为可能某一行完全为空行,此时,sbf.length()为0但并没有独到末尾,所以在判断不是末尾以后,需要继续返回这种控制。           return "";    }    //返回行号。    public int getLineNumber() {       return lineNumber;    }}

java中流操作的规律:
java中对流的操作,一定需要明确流的传出目标地,以及源文件。
关于传输的源与目标:统一的可以分为:
    录入位置:
                    文件(硬盘):是不是文本文档:是->Reader,需要提速->BufferedReader.
                                                                         否->InputStream,需要提速->缓冲字节流

                    键盘-->System.in,因为需要转换为文档,需要使用字节字符流,InputStreamReader(System.in)

                    内存-->这个需要针对Array操作。
    输出位置:
                    文件-->是不是文档-->是-->Writer
                                                       否-->OutputStream      
                    控制台-->System.out,-->是否需要独处方便:OutputStreamWriter(System.out);

                    内存。
// 键盘录入,回车打印,输入over结束。public static void test() throws IOException {InputStream is = System.in;StringBuilder strb = new StringBuilder();int i = 0;while (true) {i = is.read();if (((char) i) == '\r')continue;if (((char) i) == '\n') {if ("over".equals(strb.toString()))break;System.out.println(strb.toString().toUpperCase());strb.delete(0, strb.length());} else {strb.append((char) i);}}}        //使用字节转字符流,将输入的一行文字展示在控制台上。每输入一次就打印一次。public static void byteToChar() throws IOException {InputStream is = System.in;InputStreamReader isr = new InputStreamReader(is);BufferedReader br = new BufferedReader(isr);OutputStream out = System.out;OutputStreamWriter osw = new OutputStreamWriter(out);BufferedWriter bw = new BufferedWriter(osw);String str = null;while ((str = br.readLine()) != null) {if ("over".equals(str))// 注意str不应该放前边,应为防止其为空。break;bw.write(str.toUpperCase());bw.newLine();bw.flush();}}}

使用System类(java.lang)的特有方法改变程序的(System.in,System.out)标准输出输入流默认位置:

             1)setIn()

                    static void setIn(InputStream in)重新分配“标准”输入流。  

              2)setOut()

                    static void setOut(PrintStream out)重新分配“标准”输出流。

java中一些其他的流对象,
            字节打印流:PrintStream
            字符打印流:  PrintWriter
        向文本输出流打印对象的格式化表示形式。此类实现在 PrintStream 中的所有 print 方法。它不包含用于写入原始字节的方法,对于这些字节,程序应该使用未编码的字节流进行写入。 
        
与 PrintStream 类不同,如果启用了自动刷新,则只有在调用 println、printf 或 format   的其中一个方法时才可能完成此操作,而不是每当正好输出换行符时才完成。  这些方法使用平台自有的行分隔符概念,而不是换行符。  此类中的方法不会抛出 I/O 异常,尽管其某些构造方法可能抛出异常。  客户端可能会查询调用 checkError() 是否出现错误。

 public static void printWriter() throws IOException{BufferedReader bfr = new BufferedReader(new InputStreamReader(System.in));PrintWriter ow = new PrintWriter(System.out,true);String str = null;while((str = bfr.readLine())!=null){if("over".equals(str))break;ow.println(str.toUpperCase());}ow.close();bfr.close();}

合并流:SequenceInputStream
构造方案: 

SequenceInputStream(Enumeration<? extends InputStream> e) :他接受一个有InputStream组成的Enumeration,或者SequenceInputStream(InputStream s1, InputStream s2) 或者接收若干个按顺序的字节流对象。
  public static void sequence() throws IOException{Vector<FileInputStream> vector  = new Vector<FileInputStream>();vector.add(new FileInputStream("test.txt"));vector.add(new FileInputStream("test000.txt"));vector.add(new FileInputStream("test001.txt"));Enumeration<FileInputStream> en = vector.elements();SequenceInputStream sis = new SequenceInputStream(en);BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream("test123.txt"));byte[] buf = new byte[1024];int  i = 0;while((i=sis.read(buf))!=-1){bos.write(buf, 0, i);bos.write('A');bos.flush();}bos.close();sis.close();}
ObjectOutputStream,ObjectInputStream对象的序列化与反序列化:可以通过这两个流对象对堆内存中的对象进行硬盘存储。
被序列化的对象必须实现Serializable 接口,该接口没有没有任何方法或者字段,仅用于表示对象可序列化。

public class Play32 {public static void main(String[] args) throws IOException, ClassNotFoundException {ObjectOutputStream  oos = new ObjectOutputStream(new FileOutputStream("object.txt"));Play32_1 play1 = new Play32_1(123, "test","test1");oos.writeObject(play1);oos.close();ObjectInputStream ois = new ObjectInputStream(new FileInputStream("object.txt"));Play32_1 obj = (Play32_1) ois.readObject();System.out.println(obj.i+"|||"+obj.str+"|||"+obj.getStrr());ois.close();}}class Play32_1 implements Serializable {/** * 序列化:就是讲对内存中的成员写入到文件中。 */private static final long serialVersionUID = 444444L;//实现了Serializable接口的类都会有一个UID的序列号(java自动生成)标示,类改变,序列号也会改变。不过这样显示的手动写入,则不会改变。transient int i;//被transient修饰的成员不会被序列化。String str;static String strr = "cn";//静态不会被序列化。因为他不在队内村中。public Play32_1(int i, String str,String strr) {this.i = i;this.str = str;this.strr = strr;}public int getI() {return i;}public void setI(int i) {this.i = i;}public String getStr() {return str;}public void setStr(String str) {this.str = str;}public static String getStrr() {return strr;}public static void setStrr(String strr) {Play32_1.strr = strr;}}




原创粉丝点击