java基础知识整理(输入输出)

输入输出:
使用输入机制,允许程序读取外部数据(包括来自磁盘,光盘等存储设备的数据),用户输入数据;
使用输出机制:允许程序疾苦运行状态,将程序数据输出到磁盘,光盘等存储设备
Java的IO支持通过Java.io包下的类和接口来支持,在java.io包下主要包括输入,输出两种IO流,每种输入,输出又可分为字节流和字符流两大类。其中字节流以字节为单位来处理输入输出操作,而字符流字符流则以字符来处理输入输出操作,除此之外,Java的Io流使用了一种装饰设计模式,它将IO流分成底层节点流和上层处理流,其中节点流用于和底层物理存储节点直接关联。
File类:
File能新建,删除和重命名文件和目录,File不能访问文件本身内容。如果需要访问文件本身内容,则需要使用输入/输出流。
访问文件名的相关方法:
String getName():返回此File对象的所表示的文件名或路径名(如果是路径的话,返回最后一级子路径名)
String getPath():返回此File对象所对应的路径名
File getAbsoluteFile():返回此File对象所对应的绝对路径所对应的File对象
String getAbsolutePath():返回此File对象所对应的绝对路径名
String getParent():返回此File对象对应目录(最后一级子目录)的父目录名
Boolean renameTo(File newName):重命名此File对象对应的文件或目录,如果重命名成功返回true,否则返回false。
文件相关检测方法
Boolean exits():判断File对象对应的文件或目录是否存在
Boolean canWrite():判断File对象对应的文件和目录是否可写
Boolean canRead():判断File对象所对应的文件和目录是否可读
Boolean isFile():判断File对象所对应的是否是文件,不是目录
Boolean isAbsolute():判断File对象所对应的文件或目录是否是绝对路径。该方法消除了不同平台的差异,可以直接判断File对象是否为绝对路径。在Unix/Linux等系统上,如果路径名开头是一条斜线(\),则表明该File对象对应一个绝对路径;在Windows等系统上,如果路径开头是盘符,则说明它是一个绝对路径
获取常规文件信息

  1. long lastModified():返回文件的最后修改时间

  2. long Length():返回文件内容的长度
    文件操作相关方法

  3. Boolean createNewFile():当此File对象所对应的文件不存在时,该方法将新建一个该File对象所指定的新文件,创建成功返回true;否则返回false

  4. Boolean delete():删除File对象所对应的文件或路径。

  5. Static File createTempFile(String prefix,String suffix):在默认临时文件目录中创建一个临时的空文件,使用给定前缀,系统生成的随机数和给定后缀作为文件名。这是一个静态方法,可以直接通过File类来调用。Prefix参数至少必须是三个字节长。建议前缀使用一个短的,有意义的字符串。Suffix参数可以为null,在这种情况下,将使用默认后缀“.tmp”

  6. Static File createTempFile(String prefix,String suffix,File directory):在directory所指定的目录中创建一个临时的空文件,使用给定前缀,系统生成随机数和给定后缀作为文件名。这是一个静态方法,可以直接通过File类来调用。

  7. Void deleteOnExit():注册一个删除钩子,指定当Java虚拟机退出时,删除File对象所对应的文件和目录。
    目录操作的相关方法:
    Boolean mkdir():试图创建一个File对象所对应的目录,如果创建成功,则返回true,否则返回false。调用该方法时File对象必须对应一个了路径,而不是一个文件。
    String[] list():列出File对象的所有子文件名和路径名,而不是一个文件
    File[] listFiles():列出File对象的所有子文件和路径,返回File数组
    Static File[] listRoots():列出系统所有的根路径,可以直接用Flie类来调用
    如:
    public class FileTest {
    public static void main(String[] args) throws IOException {
    //以当前路径创建一个File对象
    File file=new File(".");
    //直接获取文件名
    System.out.println(file.getName());
    //获取相对路径的父路经可能出错
    System.out.println(file.getParent());
    //获取绝对路径
    System.out.println(file.getAbsoluteFile());
    //获取上一级路径
    System.out.println(file.getAbsoluteFile().getParent());
    //在当前路径下创建一个临时文件
    File tmpFile=File.createTempFile(“aaa”, “.txt”,file);
    //指定当JVM退出时删除该文件
    tmpFile.deleteOnExit();
    //以系统当前时间作为新文件名创建新文件
    File newFile=new File(System.currentTimeMillis()+"");
    System.out.println(“newFile对象是否存在:”+newFile.exists());
    //以指定newFile对象创建一个文件
    newFile.createNewFile();
    //以newFile对象创建一个目录,因为newFile已经存在
    //所以下面将返回false,即无法创建该目录
    newFile.mkdir();
    //使用list方法来列出当前路径下所有文件和路径
    String[] fileList=file.list();
    System.out.println("==========当前路径下所有文件和路径如下=");
    for (String fileName : fileList) {
    System.out.println(fileName);
    }
    //ListRoots静态方法列出所有的磁盘根历经
    File[] roots=File.listRoots();
    System.out.println("====系统所有根目录");
    for (File root : roots) {
    System.out.println(root);
    }
    }
    }
    输出:.
    null
    D:\Java\File.
    D:\Java\File
    newFile对象是否存在:false
    ==========当前路径下所有文件和路径如下=
    .classpath
    .project
    .settings
    1564362341460
    aaa8995240427698729221.txt
    bin
    src
    ====系统所有根目录
    C:
    D:
    E:
    F:
    Wondows的路径分割符使用反斜杠(\),而Java程序中的反斜杠表示转义字符,所以需要在Windows中路径下包括反斜线,应该用两条反斜线,或者直接使用斜线也可以,Java程序支持将斜线当成平台无关的路径分隔符。
    文件过滤器:
    在File的list方法中可以接受一个FilenameFilter参数,通过该参数可以只列出符合条件的文件。
    FilenameFilter接口里包含了一个accept(File dir,String name)方法,该方法将以此对制定File的所有子目录,子文件夹进行迭代,如果方法返回true,则list方法会列出该子目录或者子文件夹。
    //实现自己的FilenameFilter实现类
    public class MyFilenameFilter implements FilenameFilter
    {
    public boolean accept(File dir,String name)
    {
    //如果文件名以.java 结尾,或者文件对应一个路径,返回true
    return name.endsWith(".java")||new File(name).isDirectory();
    }
    }
    public class FilenameFilter {
    public static void main(String[] args) {
    File file=new File(".");
    String[] nameList=file.list(new MyFilenameFilter());
    for (String name : nameList) {
    System.out.println(name);
    }
    }
    }
    Java使用了使用了accept方法来封装该代码块,我们传入的M有FilenameFilter对象唯一的作用就是传入accept方法的方法体,该方法指定哪一些文件被列出。
    理解Java的IO流
    流的分类:
    输入流和输出流:
    按照流的流向来分,可以分为输入流和输出流:
    输入流:只能从中读取数据,而不能向其写出数据。
    输出流:只能向其写出数据,而不能从中读取数据
    在这里插入图片描述
    Java的输入流主要由InputStream和Reader作为基类,而输出流主要由OutputStream和Writer作为基类。
    字节流和字符流:
    字节流操作的最小数据单元是8位的子节,而字符流操作的最小数据单元是16位的字符
    字节流主要由InputStream和Output Stream作为基类,而字符流主要由Reader和Writer作为基类。
    节点流和处理流:
    按照流的角色分,可以分为节点流和处理流
    可以从/向一个特定的IO设备(如磁盘,网络)读写数据的流,称为节点流,节点流常常也被称为低级流。当使用节点流来进行输入/输出时,程序直接连接到实际的数据源,和师姐的输入/输出节点连接。
    处理流则用于对一个已经存在的流进行连接或封装,通过封装后流来实现数据的读/写功能。处理流也被称为高级流。如:
    在这里插入图片描述
    当使用处理流来进行输入输出时,程序并不会直接连接到实际的数据源,没有和实际的输入输出节点连接。使用处理流的好处:只要使用相同的处理流,程序就可以采用完全相同的输入输出代码来访问不同的数据源,随着处理流所包装的节点流的改变,程序实际所访问的数据源也相应的发生改变。
    处理流也被称为包装流
    流的概念模型:
    Java的IO流都是从四个抽象基类派生出来的,
    InputStream/Reader:所有输入流的基类,前者是字节输入流,后者是字符输入流。
    OutputStream/Writer:所有输出流的基类,前者是子接输出流,后者是字符输出流。
    在这里插入图片描述
    JavaIO流的基本概念模型,Java的处理流模型则体现了Java输入/输出流涉及的灵活性。处理流的功能主要体现在两个方面:

  8. 性能的提高:主要以增加缓冲的方式来提高输入/输出的效率

  9. 操作的便捷:处理流可能提供了系列便捷的方法来一次输入/输出大批量的内容。而不是输入/输出一个或多个“水滴“
    字节流和字符流 :
    字节流操作的数据单元是字节,字符流操作的数据单元是字符。
    InputStream和Reader:
    InputStream和Reader是所有输入流的基类,他们都是两个抽象类,本身并不能创建实例来执行输入,但他们将成为所有输入流的模板,所以他们的方法是所有输入流都可以使用的方法。
    InputStream里包含如下三个方法:

  10. int read():从输入流中读取单个子节,返回所读取的字节数据(字节数据可直接转化成int类型)

  11. int read(byte[] b):从输入流中读取最多b.length个字节数据,并将其存储在字节数组b中,返回实际读取的字节数。

  12. int read(byte[] b,int off,int len):从输入流中读取最多len字节的数据,并将其存储在数组b中,放入b数组中时,并不是从数组起点开始,而是从off位置开始,返回实际读取的字节数。
    在Reader里包含如下三个方法:
    Int read():从输入流中读取单个字符,返回所读取的字符数据。
    Int read(char[] cbuf):从输入流中读取最多的cbuf.length个字符数据,并将其存储在字符数组cbuf中,返回实际读取的字符数。
    Int read(char[] cbuf,int off,int len):从输入流中读取最多len个字符数据,并将其存储在字符数组cbuf中,放入cbuf数组中,并不是从数组起点开始,而是从off位置开始,返回实际读取的字符数。
    FileInputStream和FileReader,他们都是节点流——会直接和指定文件关联
    public class FileInputStreamTest {
    public static void main(String[] args) throws Exception {
    //创建字节输入流
    FileInputStream fis=new FileInputStream(“FileInputStreamTest.java”);
    //创建长度为1024的数组
    byte[] bbuf=new byte[1024];
    //用于保存实际读取的字节数
    int hasRead=0;
    //使用循环来重复读取
    while((hasRead=fis.read(bbuf))>0)
    {
    System.out.print(new String(bbuf,0,hasRead));
    }
    //关闭文件输入流,放在finally块里安全
    fis.close();
    }
    }
    如:
    public class FileReaderTest {
    public static void main(String[] args) throws IOException {
    FileReader fr=null;
    try {

    	//创建字符输入流
    	fr=new FileReader("FileReaderTest.java");
    	char[] cbuf=new char[32];
    	int hasRead=0;
    	while((hasRead=fr.read(cbuf))>0)
    	{
    		System.out.println(new String(cbuf,0,hasRead));
    	}
    } catch (IOException e) {
    	// TODO: handle exception
    	e.printStackTrace();
    }
    finally {
    	if(fr!=null)
    	{
    		fr.close();
    	}
    }
    

    }
    }
    InputStream和Writer还支持如下几个方法来移动记录指针:

  13. void mark(int readAheadLimit):在记录指针当前位置记录一个标记(mark)

  14. Boolean markSupported():判断此输入流是否支持mark()操作,即是否支持记录标记

  15. Void reset():将此流的记录指针重新定位到上一次记录标记(mark)位置。

  16. Long skip(long n):记录指针向前移动n个字节/字符
    Output Stream和Writer
    提供了三个方法:void writer(int c):将指定的字节/字符输出到输出流中,其中c既可以代表字节,也可以代表字符。
    Void write(byte[] /char[] buf):将字节数组/字符数组中的数据输出到指定输出流中
    Void write(byte[]/char[] buf/,int off,int len):将字节数组/字符数组中从off位置开始,长度为len的字节/字符输出到输出流中。
    因为字符流直接以字符作为操作单位,所以Writer可以用字符串来代替字符数组,即以String对象作为参数。Writer里还包含如下两个方法:
    Void write(String str):将str字符串里包含的字符输出到指定输入流中。
    Void write(String str,int off,int len):将str字符串列里从off开始,长度为len的字符输出到指定输出流中。
    public class FileOutputStreamTest {
    public static void main(String[] args) throws IOException {
    FileInputStream fis=null;
    FileOutputStream fos=null;
    try {
    //创建字节输入流
    fis=new FileInputStream(“FileOutputStreamTest.java”);
    //创建字节输出流
    fos=new FileOutputStream(“newFile.txt”);
    byte[] bbuf=new byte[32];
    int hasRead=0;
    //循环从输入流中读取数据
    while((hasRead=fis.read(bbuf))>0)
    {
    fos.write(bbuf,0,hasRead);
    }
    } catch (IOException e) {
    // TODO: handle exception
    e.printStackTrace();
    }
    finally {
    if(fis!=null)
    {
    fis.close();
    }
    if(fos!=null)
    {
    fos.close();
    }
    }
    }
    }
    使用Java的io流执行输出时,不要忘记关闭输入流,关闭输入流可以保证流的物理资源被回收之外,可能还可以将输出流缓冲中的数据Flush到物理节点里(相当于在执行close方法之前,自动执行输出流的flush()方法)。
    public class FileWriterTest {
    public static void main(String[] args) throws IOException {
    FileWriter fw=null;
    try {
    //创建字符输出流
    fw=new FileWriter(“pome.txt”);
    fw.write(" 锦瑟 —李商隐\r\n");
    fw.write(“锦瑟无端五十弦,一弦一柱思华年。\r\n”);
    fw.write(“庄生晓梦迷蝴蝶,望帝春心托杜鹃。\r\n”);
    fw.write(“沧海月明珠有泪,蓝田日暖玉生烟。\r\n”);
    fw.write(“此情可待成追忆,只是当时已惘然。\r\n”);
    } catch (IOException e) {
    // TODO: handle exception
    e.printStackTrace();
    }
    finally {
    //使用Finally块来关闭文件输入流
    if(fw!=null)
    {
    fw.close();
    }
    }
    }
    }
    在输出字符串内容时,字符串内容的最后是\r\n,这是Windows平台的换行符,通过这种方式就可以让输出内容换行;如果是Unix/Linux/BSD等平台,只要使用\n就可以作为换行符。
    输入/输出流体系:
    处理流的功能,他可以隐藏底层设备上节点流的差异,并对外提供更加方便的输入/输出方法,让程序员只需要关心高级操作。
    使用处理流的典型思路:使用处理流来包装节点流,程序通过处理流来执行输入/输出功能,让节点流与底层的I/O设备,文件交互。
    只要流的构造器不是一个物理节点,而是已经存在的流,那么这种流一定是处理流;而所有节点流都是直接以物理IO节点作为构造器参数的。
    如:
    public class PrintStreamTest {
    public static void main(String[] args) {
    PrintStream ps=null;
    try {
    //创建一个节点输出流
    FileOutputStream fos=new FileOutputStream(“test.txt”);
    //以Print Stream来包装FileOutputStream输出流
    ps=new PrintStream(fos);
    //使用Print Stream执行输出
    ps.println(“普通字符串!”);
    //直接使用PrintStream输出对象
    ps.println(new PrintStreamTest());
    } catch (IOException e) {
    // TODO: handle exception
    e.printStackTrace();
    }
    finally {
    if(ps!=null)
    {
    ps.close();
    }
    }
    }
    }
    当使用处理流来包装底层节点流之后,关闭输入/输出流资源时,只要关闭最上层的处理流即可。关闭最上层的处理流时,系统会自动关闭被该处理流包装的节点流。
    输入/输出流体系:
    在这里插入图片描述
    字节流可以处理所有的二进制文件。
    规则:如果需要进行输入输出的内容是文本内容,则应该考虑使用字符流,如果需要进行
    输入输出的二进制文件内容,则应该考虑使用字节流。
    所有能用记事本打开并看到其中字符内容文件我们称为文本文件,反之则称为二进制文件。但实质是计算机里所有的文件都是二进制文件,文本文件只是二进制文件的一种特例,当二进制文件里的内容恰好能被正常解析成字符时,则该二进制文件就变成了文本文件,Windows下简体中文的默认使用GDK编码集,而Linux下简体中文默认使用UTF-8编码集
    转换流:
    用于实现将字节流转换成字符流,其中InputStreamReader将字节输入流转换成字符输入流,Output StreamWriter将字节输出流转换成字符输出流。Java使用System.in代表标准输入,即键盘输入,但这个标准输入流是Input Stream类的实例,使用不太方便,所以使用InputStreamReader将其转化成字符输入流,普通Reader读取输入内容时依然不太方便,我们可以将普通的Reader再次包装成BufferedReader,利用BufferedReader的readLine方法可以一次读取一行内容。如:
    public class KeyinTest {
    public static void main(String[] args) {
    BufferedReader br=null;
    try {
    //将System。in对象转化成Reader对象
    InputStreamReader reader=new InputStreamReader(System.in);
    //将普通Reader包装成BufferedReader
    br=new BufferedReader(reader);
    String buffer=null;
    //采用循环方式来一行一行的读取
    while((buffer=br.readLine())!=null)
    {
    if(buffer.equals(“exit”))
    {
    System.exit(1);
    }
    System.out.println(“输入内容:”+buffer);
    }

    } catch (IOException e) {
    	// TODO: handle exception
    	e.printStackTrace();
    }
    finally{
    	try {
    		br.close();
    	} catch (IOException e) {
    		// TODO: handle exception
    		e.printStackTrace();
    	}
    }
    

    }
    }

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值