Java не может получить путь к файлу, который существует в текущем каталоге - PullRequest
2 голосов
/ 23 августа 2011

Если файл существует в том же каталоге, где выполняется приложение Java, и я создаю объект File для этого файла, методы File File для пути к файлу также включают имя файла.Код и выходные данные приведены ниже.

Если бы это была ошибка в версии JDK, которую я использую, кто-то наверняка уже видел бы ее.getCanonicalPath () включает имя файла?Javadocs указывают, что имя каталога должно быть возвращено.

import java.io.File;
import java.io.IOException;


public class DirectoryFromFile {

    private void getDirectoryOfFile(String fileName) throws IOException{

        File f = new File(fileName );

        System.out.println("exists(): " + f.exists());
        System.out.println("getPath(): " + f.getPath());
        System.out.println("getAbsolutePath(): " + f.getAbsolutePath());
        System.out.println("getParent(): " + f.getParent() );
        System.out.println("getCanonicalPath(): " + f.getCanonicalPath() );
        System.out.println("getAbsoluteFile().getCanonicalPath(): " + f.getAbsoluteFile().getCanonicalPath() );
        String dirname = f.getCanonicalPath();
        System.out.println("dirname: " + dirname);
        File dir = new File(dirname);
        System.out.println("dir: " + dir.getAbsolutePath());

        if (dirname.endsWith(fileName))
            dirname = dirname.substring(0, dirname.length() - fileName.length());
        System.out.println("dirname: " + dirname);
        File dir2 = new File(dirname);
        System.out.println("dir2: " + dir2.getAbsolutePath());
    }

    public static void main(String[] args) {

        DirectoryFromFile dff = new DirectoryFromFile();
        try {
            dff.getDirectoryOfFile("test.txt");
        } catch (IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
    }

}

Здесь 'выходные данные:

exists(): true
getPath(): test.txt
getAbsolutePath(): C:\dean\src\java\directorytest\directory.from.file\test.txt
getParent(): null
getCanonicalPath(): C:\dean\src\java\directorytest\directory.from.file\test.txt
getAbsoluteFile().getCanonicalPath(): C:\dean\src\java\directorytest\directory.from.file\test.txt
dirname: C:\dean\src\java\directorytest\directory.from.file\test.txt
dir: C:\dean\src\java\directorytest\directory.from.file\test.txt
dirname: C:\dean\src\java\directorytest\directory.from.file\
dir2: C:\dean\src\java\directorytest\directory.from.file

До сих пор я нашел единственный способ получить каталогв этом случае стоит вручную разобрать имя файла.

Есть ли в классе File способ получить имя каталога в этом случае (где файл, существующий в текущем каталоге, создается без указания каталога)?

Ответы [ 5 ]

10 голосов
/ 23 августа 2011

Почему File.getAbsolutePath () и File.getCanonicalPath () включают имя файла? Javadocs указывают, что имя каталога должно быть вернулся.

Нет, нет. Если вы хотите указать, почему, по вашему мнению, они это делают, кто-то может определить ошибку в ваших рассуждениях. Кроме того, если вы укажете, что именно вы хотели бы видеть для вывода, учитывая какой-то конкретный вклад, мы также можем вам помочь. Название вашего вопроса также кажется странным, поскольку ваша проблема, похоже, в том, что означает , возвращая полный путь к файлу.

Редактировать: Мне кажется, я понимаю источник вашего замешательства. A File представляет путь к файловой системе независимо от платформы. Это может быть путь к файлу или каталогу. Он также всегда представляет один и тот же путь, но не обязательно один и тот же абсолютный путь. Это очень тонкое различие, но очень важное. Объект File, представляющий относительный путь, всегда относительный . Имея файл, представляющий относительный путь, вы можете получить текущий соответствующий абсолютный путь, используя getAbsolutePath (). Это, однако, не меняет того факта, что Файл представляет собой относительный путь. Дальнейшие вызовы getAbsolutePath () для одного и того же объекта File могут возвращать разные значения. Рассмотрим, например:

// A relative file
File foo = new File("foo.txt");
// Resolve relative file against CWD
System.out.println(foo.getAbsolutePath());
    // Output: D:\dev\projects\testbed\foo.txt
System.setProperty("user.dir", "C:\\somewhere");
// Resolve relative file against new CWD
System.out.println(foo.getAbsolutePath());
    // Output: C:\somewhere\foo.txt
// Get an absolute file
File absoluteFoo = foo.getAbsoluteFile();
// Show absolute path
System.out.println(absoluteFoo.getAbsolutePath());
    // Output: C:\somewhere\foo.txt
System.setProperty("user.dir", "D:\\somewhere-else");
// An absolute path doesn't change when the CWD changes
System.out.println(absoluteFoo.getAbsolutePath());
    // Output: C:\somewhere\foo.txt

Теперь должно быть ясно, что путь, который представляет Файл, это только путь: путь. Кроме того, путь может состоять из нуля или более частей, и вызов getParent () для любого файла возвращает путь к этому файлу с последним удаленным элементом пути, если не существует «последнего элемента пути» для удаления. Таким образом, ожидаемый результат new File("foo").getParent() равен null, поскольку относительный путь "foo" не имеет родителя.

Из приведенного выше примера и объяснения вы должны увидеть, что способ получить содержащий каталог при создании объекта File с относительным путем -

String absoluteParentDirPath = someRelativeFile.getAbsoluteFile().getParent();

с оговоркой, что "абсолютный путь" зависит от вашей среды в то время.

Дополнительное примечание: поскольку File является Serializable, вы можете записать файл относительного пути на диск или отправить его по сети. Этот файл после десериализации в другой JVM все равно будет представлять относительный путь и будет сопоставлен с любым текущим рабочим каталогом этой JVM.

1 голос
/ 23 августа 2011

В дополнение к существующим ответам относительно getAbsolutePath и getCanonicalPath, пожалуйста, также обратите внимание, что File.getParent() не означает «родительский каталог», это просто относится к объекту родительского файла, который использовался для создания файла .

Например, если объект файла может быть создан так:

File dir = new File("/path/to/a/directory");
File f1 = new File(dir, "x.txt");
File f2 = new File(dir, "../another/y.txt");
File f3 = new File("z.txt");

f1 будет означать /path/to/a/directory/x.txt, его родитель dir (/path/to/a/directory)

f2 будет означать /path/to/a/directory/../another/y.txt, его канонический путь будет /path/to/a/another/y.txt, но его родитель все еще является ссылкой на dir (/path/to/a/directory)

f3 будет ссылаться на z.txt в текущем каталоге. У него нет родительского файлового объекта, поэтому f3.getParent() или f3.getParentFile() вернет ноль.

1 голос
/ 23 августа 2011

Я не уверен, почему вы думаете, что Javadoc говорит, что он возвращает имя каталога.

Вот этот Javadoc -

Абстрактное представление имен файлов и каталогов.

Пользовательские интерфейсы и операционные системы используют зависящие от системы строки имен файлов для имен файлов и каталогов. Этот класс представляет абстрактное, независимое от системы представление иерархических путей. Абстрактный путь имеет два компонента:

  1. Необязательная системно-зависимая префиксная строка, такая как спецификатор дисковода, "/" для корневого каталога UNIX или "\\" для пути UNC для Microsoft Windows и
  2. Последовательность из нуля или более имен строк.

Первое имя в абстрактном пути может быть именем каталога или, в случае UNC-путей Microsoft Windows, именем хоста. Каждое последующее имя в абстрактном пути обозначает каталог; фамилия может обозначать либо каталог, либо файл. Пустой абстрактный путь не имеет префикса и пустой последовательности имен.

http://download.oracle.com/javase/6/docs/api/java/io/File.html#getAbsolutePath%28%29

Возвращает строку абсолютного пути к этому абстрактному пути .

1 голос
/ 23 августа 2011

Поведение ожидается.В документации не упоминается, что имя файла не включено.

Возможно, вас смущает разница между getAbsolutePath() и getAbsoluteFile().Дело в том, что последний возвращает File экземпляр.

0 голосов
/ 23 августа 2011

путь - это полный путь

если вам нужен только каталог, вам нужно вызвать file.getParent ()

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...