Wie lese ich eine Datei aus einem relativen Pfad in einem Java-Projekt? java.io.File kann den angegebenen Pfad nicht finden

113

Ich habe ein Projekt mit 2 Paketen:

  1. tkorg.idrs.core.searchengines
  2. tkorg.idrs.core.searchengines

In Paket (2) habe ich eine Textdatei ListStopWords.txt, in Paket (1) habe ich eine Klasse FileLoadder. Hier ist Code in FileLoader:

File file = new File("properties\\files\\ListStopWords.txt");

Aber haben Sie diesen Fehler:

The system cannot find the path specified

Können Sie eine Lösung geben, um das Problem zu beheben? Vielen Dank.

tiendv
quelle
12
Ihre beiden Paketbeispiele sind gleich. Meinst du nicht properties.filesfür 2?
BalusC

Antworten:

172

Wenn es sich bereits im Klassenpfad befindet, beziehen Sie es einfach aus dem Klassenpfad und nicht aus dem Festplattendateisystem. Spielen Sie nicht mit relativen Pfaden java.io.File. Sie hängen vom aktuellen Arbeitsverzeichnis ab, über das Sie innerhalb des Java-Codes keinerlei Kontrolle haben.

Angenommen, das ListStopWords.txtbefindet sich im selben Paket wie Ihre FileLoaderKlasse, dann tun Sie Folgendes:

URL url = getClass().getResource("ListStopWords.txt");
File file = new File(url.getPath());

Oder wenn alles, wonach Sie letztendlich suchen, tatsächlich eines InputStreamdavon ist:

InputStream input = getClass().getResourceAsStream("ListStopWords.txt");

Dies wird sicherlich dem Erstellen eines Pfads vorgezogen, new File()da dies urlmöglicherweise nicht unbedingt einen Pfad für das Festplatten-Dateisystem darstellt, sondern auch den Pfad für das virtuelle Dateisystem (was passieren kann, wenn die JAR in den Speicher anstatt in einen temporären Ordner auf dem Festplatten-Dateisystem erweitert wird). oder sogar einen Netzwerkpfad, die beide per Definition nicht vom FileKonstruktor verdaulich sind .

Wenn die Datei - wie der Paketname andeutet - tatsächlich eine vollwertige Eigenschaftendatei (mit key=valueZeilen) mit nur der "falschen" Erweiterung ist, können Sie die InputStreamsofort an die load()Methode weiterleiten .

Properties properties = new Properties();
properties.load(getClass().getResourceAsStream("ListStopWords.txt"));

Hinweis: Wenn Sie versuchen, aus dem staticKontext heraus darauf zuzugreifen , verwenden Sie FileLoader.class(oder was auch immer YourClass.class) anstelle der getClass()obigen Beispiele.

BalusC
quelle
Wurde FileLoader aus Java entfernt? Ich versuche dies aus einem statischen Kontext (Java 6) heraus zu tun und finde keine Möglichkeit, es zu importieren. Es sagt mir immer wieder, dass es nicht in einen Typ aufgelöst werden kann. Seltsamerweise wurde es während der Eingabe automatisch vervollständigt, gab mir dann aber einen Fehler.
Turbo
2
Oh, es soll ClassLoader.class sein.
Turbo
4
@turbo: FileLoaderist die eigene benutzerdefinierte Klasse von OP. Es soll genau die Klasse sein, in der Sie versuchen, die Ressource zu erhalten. So, so NameOfYourCurrentClass.class.getResourceAsStream(...). Das ClassLoader.classwird scheitern , wenn die ClassLoaderKlasse von einem anderen Classloader geladen wird, die mit einer Hierarchie von mehreren Classloader in einer „Unternehmen“ Anwendung passieren kann (wie eine Java EE Web - Anwendung).
BalusC
Ohh ich sehe. Ich habe nicht verstanden, dass es abhängig ist. Danke, dass du das geklärt hast!
Turbo
10
Irgendwelche Vorschläge, ob sich die Datei nicht im selben Paket befindet? In meinem Fall versuche ich, eine Datei zu öffnen, die sich in einem Testpaket befindet.
Robin Newhouse
44

Die folgende Zeile kann verwendet werden, wenn der relative Pfad der Datei angegeben werden soll.

File file = new File("./properties/files/ListStopWords.txt");  
Santhosh
quelle
3
Darf ich wissen, warum 3 Schrägstriche zwischen den Pfaden.
MSNaidu
Fehler:> Unzulässiges Escapezeichen im String-Literal.
IgorGanapolsky
Wie konvertiere ich dies in ein InputStream?
Igor Ganapolsky
1
@IgorGanapolskyInputStream is = new FileInputStream("./properties/files/ListStopWords.txt");
Cameron Hudson
42

Der relative Pfad funktioniert in Java mit dem. Operator.

  • . bedeutet denselben Ordner wie der aktuell ausgeführte Kontext.
  • .. bedeutet den übergeordneten Ordner des aktuell ausgeführten Kontexts.

Die Frage ist also, woher kennen Sie den Pfad, nach dem Java gerade sucht?

mach ein kleines Experiment

   File directory = new File("./");
   System.out.println(directory.getAbsolutePath());

Beobachten Sie die Ausgabe, Sie werden das aktuelle Verzeichnis kennenlernen, in dem Java sucht. Verwenden Sie von dort aus einfach den Operator ./, um Ihre Datei zu suchen.

Zum Beispiel, wenn die Ausgabe ist

G: \ JAVA8Ws \ MyProject \ content.

und Ihre Datei befindet sich im Ordner MyProject einfach verwenden

File resourceFile = new File("../myFile.txt");

Hoffe das hilft

Samrat
quelle
Nach stundenlangem Suchen lieferte mir diese Antwort die Lösung
erdostamasa
8
InputStream in = FileLoader.class.getResourceAsStream("<relative path from this class to the file to be read>");
try {
    BufferedReader reader = new BufferedReader(new InputStreamReader(in));
    String line = null;
        while ((line = reader.readLine()) != null) {
            System.out.println(line);
        }
} catch (Exception e) {
    e.printStackTrace();
}
reibungslose Riemenscheibe
quelle
1
@IgorGanapolsky ist der Name der Klasse. Sie können nur auf .classLiteral verweisen, indem Sie den vollständigen Namen der Klasse angeben.
Tomasz Mularczyk
Ich denke, es soll FileLoader sein.
Jamesdeath123
6

Versuchen .\properties\files\ListStopWords.txt

Fehler.
quelle
5

Ich hätte kommentieren können, aber ich habe weniger Repräsentanten dafür. Samrats Antwort hat den Job für mich gemacht. Es ist besser, den aktuellen Verzeichnispfad durch den folgenden Code zu sehen.

    File directory = new File("./");
    System.out.println(directory.getAbsolutePath());

Ich habe es einfach verwendet, um ein Problem zu beheben, mit dem ich in meinem Projekt konfrontiert war. Stellen Sie sicher, dass Sie ./ verwenden, um zum übergeordneten Verzeichnis des aktuellen Verzeichnisses zurückzukehren.

    ./test/conf/appProperties/keystore 
dezible
quelle
Ich führe meinen Code über Tomcat aus und daher ist das aktuelle Verzeichnis nicht der Projektordner. Wie definiere ich den relativen Pfad zum Projektstamm? Ich benutze derzeit den harten Pfad: "C: \\ Benutzer \\ Benutzer \\ Desktop \\ Repositorys \\ L1_WebShop \\ dblogs.log";
Tiago Redaelli
@TiagoRedaelli überprüfen Sie diese Fragen: stackoverflow.com/questions/12843217/…
dezible
4

Während die von BalusC bereitgestellte Antwort für diesen Fall funktioniert, wird sie unterbrochen, wenn der Dateipfad Leerzeichen enthält, da diese in einer URL in% 20 konvertiert werden, was kein gültiger Dateiname ist. Wenn Sie das Dateiobjekt mithilfe eines URI anstelle eines Strings erstellen, werden Leerzeichen korrekt behandelt:

URL url = getClass().getResource("ListStopWords.txt");
File file = new File(url.toURI());
Mark Krijgsman
quelle
2

Ich wollte 'command.json' in src / main // js / Simulator.java analysieren. Dafür habe ich die json-Datei in den src-Ordner kopiert und den absoluten Pfad wie folgt angegeben:

Object obj  = parser.parse(new FileReader("./src/command.json"));
sver
quelle
2

Geben Sie hier die Bildbeschreibung ein

Angenommen, Sie möchten aus dem resourcesVerzeichnis in der FileSystemKlasse lesen .

String file = "dummy.txt";
var path = Paths.get("src/com/company/fs/resources/", file);
System.out.println(path);

System.out.println(Files.readString(path));

Hinweis: Führen .ist nicht erforderlich.

R Sonne
quelle
0

Für mich ist das Problem tatsächlich, dass der Klassenpfad des Dateiobjekts von stammt <project folder path> or ./src. Verwenden Sie File file = new File("./src/xxx.txt");also mein Problem gelöst

J. Luan
quelle
0

String basePath = neue Datei ("myFile.txt"). GetAbsolutePath (); Diesen Basispfad können Sie als korrekten Pfad Ihrer Datei verwenden

user13499397
quelle
-1

Wenn Sie versuchen, getClass()von einer statischen Methode oder einem statischen Block aufzurufen , können Sie wie folgt vorgehen.

Sie können getClass()das PropertiesObjekt aufrufen, in das Sie laden.

public static Properties pathProperties = null;

static { 
    pathProperties = new Properties();
    String pathPropertiesFile = "/file.xml;
    InputStream paths = pathProperties.getClass().getResourceAsStream(pathPropertiesFile);
}
arun_kk
quelle
Einfach ein Schlusszitat fehlen.
Jamesdeath123
-1

Wenn die Textdatei nicht gelesen wird, versuchen Sie, einen näheren absoluten Pfad zu verwenden (wenn Sie möchten, dass Sie den vollständigen absoluten Pfad verwenden können), wie folgt:

FileInputStream fin=new FileInputStream("\\Dash\\src\\RS\\Test.txt");

Angenommen, der absolute Pfad ist:

C:\\Folder1\\Folder2\\Dash\\src\\RS\\Test.txt
KR N.
quelle