Java粗淺認識-I/O(三)

Nio2

什麼是Java Nio2,java Nio2是在java 7新增內容,在java1.4 nio的基礎上再次對I/O模型的增強,新增Path類,Files工具類,Paths工具類,主要是爲了方便文件、目錄的操作。

java.nio.file.Path

一個Path代表了一個在本地文件系統的一個路徑

1.創建一個path類

   /**
     * 創建一個Path類
     *
     * @throws URISyntaxException
     */
    private static void createPath() throws URISyntaxException {
        //1.根據文件名構建
        Path path = Paths.get("C:\\Users\\baopz\\Desktop\\圖片\\test\\test.txt");
        System.out.println(path);
        //2.根據多個文件名,子文件名構建
        Path path1 = Paths.get("C:\\Users\\baopz\\Desktop\\圖片\\test", "sub", "subTest.txt");
        System.out.println(path1);

        //3.根據統一資源定位符構建
        Path path2 = Paths.get(new URI("file:///C:/Users/baopz/Desktop/圖片/test/uri.txt"));
        System.out.println(path2);

        //4.根據FileSystems創建
        Path path3 = FileSystems.getDefault().getPath("C:", "1.txt");
        System.out.println(path3);
    }

2.Path對象和File相互轉換 Path對象轉換爲URI

   /**
     * Path對象和文件相互轉換
     * path轉換爲uri
     */
    public static void convert() {
        //path轉換爲文件
        Path path = Paths.get("c://1.txt");
        System.out.println(path);
        File file = path.toFile();
        System.out.println(file.getAbsolutePath());

        //文件轉換爲path
        File file1 = new File("C://1.txt");
        System.out.println(file1);
        Path path1 = file1.toPath();
        System.out.println(path1);

        //path轉換爲uri
        URI uri = path1.toUri();
        System.out.println(uri);
    }

3.創建孩子節點,創建兄弟節點

    /**
     * 創建孩子節點,創建兄弟節點
     */
    public static void resolve() {
        Path current = Paths.get("C:\\Users\\baopz\\Desktop\\圖片\\test");
        //創建孩子節點
        Path child = current.resolve("child");
        System.out.println(child);

        //創建兄弟節點
        Path brother = current.resolveSibling("brother");
        System.out.println(brother);
    }

4.得到文件名,以及Path類的計算操作

   /**
     * path結構,root/0/1/2/..,count不會計算root層,根節點的parent是null
     * 截取部分subPath [start,end),包含start的下標,不包含end的下標
     */
    public static void getFilename() {
        Path current = Paths.get("C:\\Users\\baopz\\Desktop\\圖片\\test\\1.txt");
        Path filename = current.getFileName();
        System.out.println(filename.toString());

        //根據計算得到文件名
        filename = current.getName(current.getNameCount() - 1);
        System.out.println(filename.toString());

        //得到根節點
        System.out.println(current.getRoot());

        //打印每一層的filename
        for (int i = 0; i < current.getNameCount(); i++) {
            System.out.println(i + "層 " + current.getName(i));
        }

        //根節點的父親節點是null
        System.out.println(current.getRoot().getParent());

        //截取部分path[start,end)
        System.out.println(current.subpath(1,3));

        //是不是以1.txt結尾的path,注意這裏不能用來判斷是不是某種格式結尾,這裏計算的最後一個節點
        //這裏返回的是true
        System.out.println(current.endsWith("1.txt"));
        //這裏返回的是false
        System.out.println(current.endsWith(".txt"));
    }

5.regex或者glob匹配

    /**
     * regex或者glob匹配
     * 匹配語法
     * 語法:模式 => {regex|glob}:pattern
     */
    public static void match() {
        Path current = Paths.get("C:\\Users\\baopz\\Desktop\\圖片\\test\\1.txt");
        FileSystem fileSystem =  FileSystems.getDefault();
        //正則表達式匹配.txt結尾
        PathMatcher pathMatcher = fileSystem.getPathMatcher("regex:.*.txt");
        System.out.println(pathMatcher.matches(current));

        //glob匹配.txt結尾
        pathMatcher = fileSystem.getPathMatcher("glob:*.txt");
        System.out.println(pathMatcher.matches(current));
        
    }

6.java.nio.file.WatchService監控器

這個功能還是非常實用的,文件監控器,可以監控文件以及目錄的變化,以及設置監控頻率,這裏是演示,會運行在main線程裏面,項目中建議開個線程單獨運行,(後面我會吧線程的相關操作列出來)。

    /**
     * 文件監控器,可以監控文件以及目錄的變化,以及設置監控頻率
     */
    public static void watchServer() throws IOException, InterruptedException {
        FileSystem fileSystem = FileSystems.getDefault();
        WatchService watchService = fileSystem.newWatchService();

        Path path = Paths.get("C:\\Users\\baopz\\Desktop\\圖片\\test");
        //監控事件,新增,修改,刪除,溢出,監控頻率=low
        path.register(watchService,new WatchEvent.Kind<?>[]{StandardWatchEventKinds.ENTRY_CREATE, StandardWatchEventKinds.ENTRY_DELETE,
                StandardWatchEventKinds.ENTRY_MODIFY, StandardWatchEventKinds.OVERFLOW},
                SensitivityWatchEventModifier.LOW);
        while (true) {
            WatchKey watchKey = watchService.take();
            for (WatchEvent<?> watchEvent : watchKey.pollEvents()) {
                //有新文件創建
                if (watchEvent.kind() == StandardWatchEventKinds.ENTRY_CREATE) {
                    Path path1 = (Path) watchEvent.context();
                    System.out.println("新建了一個文件:" + path1);
                }
                //有文件被刪除
                if(watchEvent.kind()==StandardWatchEventKinds.ENTRY_DELETE){
                    Path path1 = (Path) watchEvent.context();
                    System.out.println("刪除了一個文件:" + path1);
                }

                if (watchEvent.kind()==StandardWatchEventKinds.ENTRY_MODIFY){
                    Path path1 = (Path) watchEvent.context();
                    System.out.println("文件被修改:"+path1);
                }

                if (watchEvent.kind()==StandardWatchEventKinds.OVERFLOW){
                    System.out.println("溢出");
                }
            }
            boolean valid = watchKey.reset();
            if (!valid) {
                break;
            }
        }
    }

java.nio.file.Files、java.nio.file.FileSystems工具類

1.創建文件

    public static void createFile() throws IOException {
        Path path = Paths.get("C:\\Users\\baopz\\Desktop\\圖片\\test\\test.txt");
        //得到上一層節點
        Path parent = path.getParent();
        if (Files.notExists(parent)) {
            Files.createDirectories(parent);
        }
        //在創建文件的時候,一定要先存着上一層的目錄
        if (Files.notExists(path)) {
            Files.createFile(path);
        }
    }

2.刪除文件

    public static void delete() throws IOException {
        Path current = Paths.get("C:\\Users\\baopz\\Desktop\\圖片\\test\\1.txt");
        boolean isSuccess = Files.deleteIfExists(current);
        System.out.println(isSuccess);
    }

3.得到BufferedReader,進行字符操作

   /**
     * 字符集對應不上會拋錯
     * @throws IOException
     */
    public static void readBuffer() throws IOException {
        Path current = Paths.get("C:\\Users\\baopz\\Desktop\\圖片\\test\\1.txt");
        BufferedReader bufferedReader = Files.newBufferedReader(current, Charset.forName("gbk"));
        String line;
        while ((line = bufferedReader.readLine()) != null) {
            System.out.println(line);
        }
        bufferedReader.close();
    }

4.列出當前文件夾下所有文件

    /**
     * 列出當前目錄下所有文件
     * @throws IOException
     */
    public static void listFile() throws IOException {
        Path current = Paths.get("C:\\Users\\baopz\\Desktop\\圖片\\test");
        DirectoryStream directoryStream = Files.newDirectoryStream(current);
        for (Object aDirectoryStream : directoryStream) {
            System.out.println(aDirectoryStream);
        }
    }

5.樹遍歷

public static void walkingTheFileTree() throws IOException {
        Path current = Paths.get("C:\\Users\\baopz\\Desktop\\圖片\\test");
        Set<FileVisitOption> visitOptions = new HashSet<>();
        visitOptions.add(FileVisitOption.FOLLOW_LINKS);
        //設置開始節點,訪問操作,最大訪問深度,具體訪問操作
        Files.walkFileTree(current, visitOptions, 3, new MyFileVisitor());
    }

    public static class MyFileVisitor implements FileVisitor<Path> {

        @Override
        public FileVisitResult preVisitDirectory(Path dir, BasicFileAttributes attrs) throws IOException {
            System.out.println("訪問文件夾之前操作。" + dir);
            return FileVisitResult.CONTINUE;
        }

        @Override
        public FileVisitResult visitFile(Path file, BasicFileAttributes attrs) throws IOException {
            System.out.println("訪問當前文件:" + file);
            return FileVisitResult.CONTINUE;
        }

        @Override
        public FileVisitResult visitFileFailed(Path file, IOException exc) throws IOException {
            System.out.println("訪問文件錯誤:" + file);
            //跳過sub
            return FileVisitResult.SKIP_SUBTREE;
        }

        @Override
        public FileVisitResult postVisitDirectory(Path dir, IOException exc) throws IOException {
            System.out.println("訪問文件夾之後操作:" + dir);
            return FileVisitResult.CONTINUE;
        }
    }

6.文件屬性,以及文件操作

public static void accessFile() throws IOException {
        Path current = Paths.get("C:\\Users\\baopz\\Desktop\\圖片\\test");
        FileSystem fileSystem = FileSystems.getDefault();
        //遍歷文件支持的所有視圖
        for (String s : fileSystem.supportedFileAttributeViews()) {
            System.out.println(s);
        }

        //basic視圖
        BasicFileAttributes basicFileAttributes =  Files.readAttributes(current,BasicFileAttributes.class);
        System.out.println(basicFileAttributes.lastModifiedTime());

        //dos視圖
        DosFileAttributes dosFileAttributes = Files.readAttributes(current,DosFileAttributes.class);
        System.out.println(dosFileAttributes.isHidden());

        //複製
        Files.copy(current,current.resolve("副本"));
    }

到目前爲止,java1.7 的Nio2已經寫完了,接下來會講解關於網絡通信,還有一個異步通道會在下一章開頭講,會提一下Netty,再之後會針對Netty做專題詳細講解。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章