您的位置:首页 > 编程语言 > Java开发

java基础篇--09<java输入输出>

2016-01-25 14:36 411 查看
File类的操作基础---简单介绍

//只是new一个文件操作对象,对磁盘目前没有影响
File file = new File("Test");
//在磁盘上创建Test的文件
file.createNewFile();
//在磁盘上创建Test的文件夹
file.mkdir();
//在磁盘上创建一组文件夹
File fileA = new File("Test/asda/asda");
fileA.mkdirs();
//检验磁盘上的文件或者目录是否存在
file.exists();
//获取相对路径,比如这里的相对路径是/
//因为JVM运行在Test/下
//我们创建的文件就在Test/Test
file.getPath();
//获取绝对路径,/home/sa/sd/Test/Test
//都是获取绝对路径,只是返回值类型不同
file.getAbsoluteFile();
file.getAbsolutePath();
//返回上一级目录,已经是root就会返回一个null
file.getParent();
//返回上次修改时间
file.lastModified();
//返回文件内容的长度
file.length();
//判断是否是文件或者是否是目录
file.isDirectory();
file.isFile();
//删除,file所指向的文件或者目录
file.delete();
//删除,退出时删除
file.deleteOnExit();
//返回值不同,但都是返回file对象所有的文件和目录
file.list();
file.listFiles();
//列出系统所有的root路径
file.listRoots();


java中任何情况都可以使用”/“作为路径分割符

可以在list,列出文件和目录的时候,添加过滤器(FilenameFilter),returntrue会被列出来,因为函数式接口,所以使用lambda表达式

     file.list((dir,name)->name.endwith(".java")||
newFile(name).isDirectory());

============输入输出流介绍

OutputStream/InputStream======字节输出/输入流
Write/Read ======字符输出/输入流

基本的流可以被封装成处理流,处理流有两大优势:
1》以增加缓冲提高输入输出效率,因为,可以对基本字节/符进行批量的取出到自己的缓冲区,造成一种”伪批量操作“,用以提高效率;
2》还提供了一些便捷的方法,来处理一次输出/入大批量的内容

处理流可以理解:对基础类的封装,包装,提供一些自己的优化机制,和整合方法

======字节流(file、pipe、String、Array)

基础应用示例
1InputStream/Readr

read()                                     //return读到的一个字节/符
read(byte[]/char[]  b)			      //读b.length个字节/符的数据并放在b数组中
//return 实际读到的字节/符数(可能不足b.length)
read(byte[]/char[]  b, int off, int len)   //读len个字节/符,存在b数组中,从off位
4000
置开始读
//return 实际读到的字节/符数(可能不足len)


2OutputStream/Writer

write(int c)                                 //c可以代表字节也可以代表字符
write(byte[]/char[] buf)	             //将数组中的数据输出到指定的流中
write(byte[]/char[] buf,int off,int len)     //从数组的off位置开始,最大放入len个数据进入流

相比较 字符流有自己的直接写入String的方法
write(String str)			     //将str里包含的字符写入到指定字符流
write(String str,int off, int len) 	     //从str的off位置,最大写入len进入的流中


小程序(对前面的读写方法的小结)----copy

class Test {
//将a.txt的内容copy到b.txt
public static void main(String[] args) throws IOException {
File file = new File("a.txt");
File fileB = new File("b.txt");
//这里a.txt是假设的已有文件,用来copy
//不需要create,只要获取指向它的file对象
fileB.createNewFile();
OutputStream os = new FileOutputStream(fileB);
InputStream ip = new FileInputStream(file);

byte[] b = new byte[10];
int readByte = 0;

System.out.println("the start");
//从a.txt开始读,判断条件也可以 “!= -1”
while((readByte = ip.read(b)) > 0){
//往b.txt里写
os.write(b, 0, readByte);
}
System.out.println("the end");

//释放物理资源,这些JVM是不会去管的,之前《异常》里有提过
//因此需要我们手动释放
os.close();
ip.close();
}
}


流的close()和flush()
java很多的输出流,都会有自己的缓冲区,close()被调用时会自动执行flush()方法,而flush()方法就是用来清空这些缓冲区里的内容,将他们真正写入物理节点中

 

注意:以上都是节点流,而不是包装的处理流,故而操作繁琐,这里所说的“包装”,即装饰者模式

======处理流

基本:
1》对字节流的包装,提供包装好的方法;更加高效;
2》字节流是以具体的物理节点(文件)作为构造参数;
而处理流是以具体的字节流作为构造参数;

close()处理流后,会自动关闭其包装的字节流;

一、转换输出/输入流
可以理解为一种特殊的处理流,可以将字节流转换成字符流,OutputStreamWriter/InputStreamReader传入相应的字节流即可

二、推回输入流

          1》PushBackInputStream/PushBackReader
               unread(byte[]/char[] buf)

                   
unread(byte[]/char[]buf,int off,int len)

               unread(int b) //b可以代表一个字节/符
             原理:会有自己的推回缓冲区,read的话会先将推回缓冲区的东西读完,才去相应的流中抓
取数据,
                         另外,推回的内容超过了,缓冲区的大小会导致错误,在new的时候,需要手动设置缓冲区的
                         大小,默认值是1

重定向标准输入输出流
在System类中有一些静态方法提供使用,用来修改默认的系统输出/输入流
1》setErr(PrintStreamerr)
2》setIn(InputStreamin)
3》setOut(PrintStreamout)

RandomAccessFile(这里Random作”任何“来理解,而不是“随机”)

          1》可以从文件任意的位置开始读取讯息
          2》可以在文件末尾追加内容
          3》但是只支持file这种IO节点操作,对于其他的IO节点就不行了

         
为了实现1》任何这种说法,必然要添加对文件指针的操作:
          long getFilePointer():
返回指针的当前位置
          void seek(long pos):
移动指针到pos位置

注意:不能用来执行插入操作,因为从你seekpos后面写的内容的效果是覆盖,这样追加完全没有问题,但是用来插入操作就不行了

前面讲了File的用法,现在讲讲Path+Paths+Files
1》Paths提供静态方法,通过文件来获取Path
Pathpath = Paths.get("src/com/jim/Test.java");

          2》Path是以JVM运行的路径为准,这个绝对/相对路径的机制和1.中说的file的机制一样,可
去参考一下,Path的基本方法也和file类似

          Path比File多出一个对文件变化的监听,

Path path = Paths.get("/home/njd/Test.java");
//直接从系统的文件系统拿到watchService
WatchService watchService = FileSystems.getDefault().newWatchService();
//注册到path开始使用
path.register(watchService, StandardWatchEventKinds.ENTRY_CREATE,
StandardWatchEventKinds.ENTRY_DELETE,
StandardWatchEventKinds.ENTRY_MODIFY);

//然后使用watchService对象,来进行监听
//这里可以使用
//watchService.poll(); 无阻塞
//watchService.poll(timeout, unit) 等待一定时间
//watchService.take() 阻塞
WatchKey key = watchService.take();
for(WatchEvent<?> event: key.pollEvents()){
System.out.println("FileName: "+event.context()+"TYPE: "+event.kind());
}


         3》Files提供了很多关于文件的Static操作方法,需要传参Path,和一些输入/输出来完成
        
示例:

                 =====基本操作

Path path = Paths.get("/home/njd/Test.java");

//copy
Files.copy(path, new FileOutputStream("a.txt"));

//gbk 控制编码方式 类似读文件的操作
List<String> lines = Files.readAllLines(path,
Charset.forName("gbk"));

//write
List<String> bytes = new ArrayList<>();
bytes.add("窗前明月光");
bytes.add("疑是地上霜");
Files.write(path, bytes, Charset.forName("gbk"));

//length()
Files.size(path);


                 ====进阶操作
                        Files可以进行遍历操作

//遍历的结果会体现在FileVisitor这个Listener中,FileVisitor对象也可以是
//个SimpleFileVisitor<Path>对象
Files.walkFileTree(path, new FileVisitor<Path>() {

@Override
public FileVisitResult postVisitDirectory(Path dir, IOException exc)
throws IOException {
//遍历目录之后
return null;
}

@Override
public FileVisitResult preVisitDirectory(Path dir,
BasicFileAttributes attrs) throws IOException {
// 遍历目录之前
return null;
}

@Override
public FileVisitResult visitFile(Path file,
BasicFileAttributes attrs) throws IOException {
//遍历文件之时
return null;
}

@Override
public FileVisitResult visitFileFailed(Path file, IOException exc)
throws IOException {
// 遍历文件失败
return null;
}
});


Files新加的功能

Pathpath
= Paths.get("Test.java");

//获取Test.java的文件属性,其中,type可选
//AclFileAttributeView:
ACL及文件所有者属性
//BasicFileAttributeView:
文件的基本属性,包括文件的最后修改时间,最后访问时间,创建时间
//DosFileAttributeView:
Dos属性,是否只读、隐藏、系统文件
//FileOwnerAttributeView:
获取或修改文件的所有者
//PosixFileAttributeView:
修改所有者、组所有者、访问权限(unixchmod干的事)

//此函数会返回一个DosFileAttributeView,可凭借这个来操作文件的属性

DosFileAttributeView
dosView = Files.getFileAttributeView(path,AclFileAttributeView.class);
dosView.setHidden(true);
dosView.serReadOnly(true);
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  Java基础