我曾使用Files.WalkFileTree()
过导航文件夹和计数音频文件的功能,但是遇到tar文件时会出现问题,似乎将其视为实际的文件夹,我希望它会跳过它。
我看不到任何可以控制这种行为的选项
码:
package com.jthink.songkong.fileloader;
import com.jthink.songkong.cmdline.SongKong;
import com.jthink.songkong.ui.MainWindow;
import java.nio.file.*;
import java.nio.file.attribute.BasicFileAttributes;
import java.util.concurrent.Callable;
import java.util.logging.Level;
/**
* Count the number of files that can be loaded, for information purposes only
*/
public class CountFilesinFolder implements Callable<Boolean> {
public static class CountFiles
extends SimpleFileVisitor<Path> {
private int fileCount = 0;
private final PathMatcher matcher;
CountFiles(String pattern) {
matcher =
FileSystems.getDefault()
.getPathMatcher("regex:" + pattern);
}
/**
* Find Music file
*
* @param file
* @param attr
* @return
*/
@Override
public FileVisitResult visitFile(Path file,
BasicFileAttributes attr) {
Path name = file.getFileName();
if (name != null && matcher.matches(name)) {
fileCount++;
}
return FileVisitResult.CONTINUE;
}
public int getFileCount() {
return fileCount;
}
}
private Path scanDir;
public CountFilesinFolder(Path scanDir) {
this.scanDir = scanDir;
}
public Boolean call() {
CountFiles countFiles = null;
try {
countFiles = new CountFiles("^(?!._).*[.](?:mp3|mp4|m4p|m4b|m4a|ogg|flac|wma)$");
Files.walkFileTree(scanDir, countFiles);
}
catch (Exception e) {
MainWindow.logger.log(Level.SEVERE, "Unable to find file for deriving base folder", e);
}
MainWindow.logger.severe("Music File Count:"+countFiles.getFileCount());
SongKong.setMaxProgress(countFiles.getFileCount());
return true;
}
}
给出这个堆栈跟踪
java.nio.file.NoSuchFileException: Z:\Scratch\fred.tar
at sun.nio.fs.WindowsException.translateToIOException(WindowsException.java:79)
at sun.nio.fs.WindowsException.rethrowAsIOException(WindowsException.java:97)
at sun.nio.fs.WindowsException.rethrowAsIOException(WindowsException.java:102)
at sun.nio.fs.WindowsDirectoryStream.<init>(WindowsDirectoryStream.java:86)
at sun.nio.fs.WindowsFileSystemProvider.newDirectoryStream(WindowsFileSystemProvider.java:526)
at java.nio.file.Files.newDirectoryStream(Files.java:411)
at java.nio.file.FileTreeWalker.walk(FileTreeWalker.java:179)
at java.nio.file.FileTreeWalker.walk(FileTreeWalker.java:199)
at java.nio.file.FileTreeWalker.walk(FileTreeWalker.java:69)
at java.nio.file.Files.walkFileTree(Files.java:2591)
at java.nio.file.Files.walkFileTree(Files.java:2624)
at com.jthink.songkong.fileloader.CountFilesinFolder.call(CountFilesinFolder.java:68)
at com.jthink.songkong.fileloader.CountFilesinFolder.call(CountFilesinFolder.java:15)
at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:334)
at java.util.concurrent.FutureTask.run(FutureTask.java:166)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1110)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:603)
at java.lang.Thread.run(Thread.java:722)
但这是一个远程驱动器(nas驱动器),我在本地驱动器上没有得到这样的错误
编辑 基于以下我认为可行的答案实施了以下内容
@Override
public FileVisitResult preVisitDirectory(Path dir,
BasicFileAttributes attrs)
throws IOException {
if(dir.endsWith(".tar"))
{
return FileVisitResult.SKIP_SUBTREE;
}
return super.preVisitDirectory(dir, attrs);
}
但是我的测试不对劲,它实际上不起作用,因为FileTreeWalker中失败的代码在previsit方法之前被调用
try {
DirectoryStream<Path> stream = null;
FileVisitResult result;
// open the directory
try {
stream = Files.newDirectoryStream(file);
} catch (IOException x) {
return visitor.visitFileFailed(file, x);
} catch (SecurityException x) {
// ignore, as per spec
return FileVisitResult.CONTINUE;
}
// the exception notified to the postVisitDirectory method
IOException ioe = null;
// invoke preVisitDirectory and then visit each entry
try {
result = visitor.preVisitDirectory(file, attrs);
if (result != FileVisitResult.CONTINUE) {
return result;
}
解决当前问题的方法:
但是实现一个visitFileFailed,您应该可以。
public class MyFileVisitor extends SimpleFileVisitor<Path> {
@Override
public FileVisitResult visitFileFailed(Path file, IOException exc) throws IOException {
if (file.toString().endsWith(".tar")) {
return FileVisitResult.CONTINUE;
}
return super.visitFileFailed(file, exc);
}
}
更新:如果我们仔细观察,可以看到walkFileTree使用Files.readAttributes
,该文件转向正在使用的当前提供程序:WindowsFileSystemProvider.readAttributes来确定路径是否为目录。
正如评论中提到的那样,我也不认为错误在于Java实现,而是OS本地调用返回错误的属性
如果要解决此问题,一种选择是实现自己的文件系统,该文件系统透明地包装WindowsFileSystem实现,但readAttributes返回.tar-
paths作为文件而不是dir。
我的Spring启动应用程序, 在获得Whitelabel错误页面后,我在我的一个控制器中映射了, 我映射了一个,出现以下异常:, 遵循User9123的解决方案,但是,我仍然得到下面的页面,
问题内容: 我在用于SQLite的JDBC驱动程序中有问题。 我正在用SELECT语句执行查询。 如果我得到一个空(0行),则在调用时会抛出“ Closed ResultSet”异常。 没有大量的JDBC经验,我的理论(我无法通过JavaDocs确认)是 对空(零行)结果集不起作用(通过设计或由于错误) 的“打开”标志设置为零行(同样是设计或错误) 我看到了此错误报告,但不确定是否相关。 我的要求
我正在尝试使用Java中的Apache commons compress将tar文件解压缩为。我能够解压缩大部分的tar文件,但很少有失败的,除了下面的例外。我不确定是什么引起了这个问题。tar文件是否已损坏?我可以在windows中使用7zip解压缩文件,但相同的文件在编程解压缩时失败。我正在使用Appache commons-compress1.18 下面是我的代码
我必须点击页面上的某个按钮。但是,当我检索所有具有特定类名的元素时。当我尝试执行每个元素或单击时,所有检索到的元素都会抛出一个过时的引用异常。我不能双击任何一个。它找到了正确的元素,但抛出了所有元素的例外。注释掉的代码就是我试图选择并点击相应按钮的地方。我附上了表格的照片。请注意,每次单击或执行按钮时,页面都会发生更改。选择上传BOM按钮是您需要特别注意的。网站
我想上传一个文件到不同的服务器使用卷曲。我读过许多类似的问题,但我没有得到任何解决我的问题。下面是我现在得到的代码: 当我运行此脚本时,它将保持运行200秒,并以以下方式响应: Sep 17 20:56:58 xxxxx vsftpd[2613]:[user]确定登录:客户端“yyyyy” Sep 17 20:56:58 xxxxx vsftpd[2618]:[用户]FTP响应:客户端“YYYYY
我在Mac OS Big Sur 11.4上使用zsh,我尝试在格式的外部usb驱动器上执行chmod。但是,它没有像预期的那样工作。为什么?