14

2 つのファイルのデータを比較する必要があるプログラムを Java で作成しています。ファイル 1 の各行をファイル 2 の各行と照合し、一致が見つかった場合は、それらを 3 番目のファイルに書き込む必要があります。ファイル 2 の最後まで読み取った後、ポインターをファイルの先頭にリセットするにはどうすればよいですか?

public class FiFo {
    public static void main(String[] args) 
    {
        FileReader file1=new FileReader("d:\\testfiles\\FILE1.txt");
        FileReader file2=new FileReader("d:\\testfiles\\FILE2.txt");
        try{
            String s1,s2;
            while((s1=file1.data.readLine())!=null){
                System.out.println("s1: "+s1);
                while((s2=file2.data.readLine())!=null){
                    System.out.println("s2: "+s2);
                }
            }
            file1.closeFile();
            file2.closeFile();
        }catch (IOException e) {
            e.printStackTrace();
        }
    }
}

class FileReader {
    BufferedReader data;
    DataInputStream in;

    public FileReader(String fileName)
    {
        try{
            FileInputStream fstream = new FileInputStream(fileName);
            data = new BufferedReader(new InputStreamReader(fstream));
        }
        catch (IOException e) {
            e.printStackTrace();
        }
    } 

    public void closeFile()
    {
        try{
            in.close();
        }
        catch (IOException e) {
            e.printStackTrace();
        }
    }
}
4

10 に答える 10

15

RandomAccessFileはあなたが必要なものだと信じています。含まれています:RandomAccessFile#seekRandomAccessFile#getFilePointer

rewind()seek(0)

于 2010-02-09T04:27:18.237 に答える
5

HashMap最善の方法は、ファイル 1 の各行を;に入れることだと思います。HashMap次に、ファイル 1 の各行ごとにファイル全体を 1 回読み取るのではなく、ファイル 2 の各行のメンバーシップを確認できます。

しかし、ファイルの先頭に戻る方法についての質問に答えるには、別のInputStream/を開くのが最も簡単な方法ですReader

于 2010-02-09T04:22:43.177 に答える
2

明らかに、次のようにファイルを閉じて再度開くことができます。

     while((s1=file1.data.readLine())!=null){
         System.out.println("s1: "+s1);
         FileReader file2=new FileReader("d:\\testfiles\\FILE2.txt");
         while((s2=file2.data.readLine())!=null){
             System.out.println("s2: "+s2);
             //compare s1 and s2;
         }
         file2.closeFile()
     }

しかし、このアルゴリズムの実行時間は O(n 2 )であるため、実際にはそのようにしたくありません。ファイル A に 1000 行、ファイル B に 10000 行ある場合、内側のループは 1,000,000 回実行されます。

あなたがすべきことは、各行を読んでコレクションに保存することです。これにより、アイテムが既に含まれているかどうかをすばやく確認できます (おそらく HashSet)。

ファイル 2 のすべての行がファイル 1 に含まれていることを確認するだけでよい場合は、ファイル 1 の各行を HashSet に追加し、ファイル 2 のすべての行がそのセットに含まれていることを確認します。

一方に含まれるすべての文字列を見つける相互比較を行う必要がある場合は、各ファイルに 1 つずつ、合計 2 つのハッシュ セットが必要になります。(ただし、1つだけを使用するためのトリックがあります)

ファイルが大きすぎて十分なメモリがない場合、元の n 2メソッドはとにかく機能しません。

于 2010-02-09T05:38:10.300 に答える
1

まあ、Gennady S.の答えは、私があなたの問題を解決するために使用するものです。

2 つのファイルのデータを比較する必要があるプログラムを Java で作成しています。

ただし、これを再度コーディングしたくない.. http://code.google.com/p/java-diff-utils/のようなものを使用したい

于 2010-02-09T05:13:29.127 に答える
1

他の人が示唆しているように、問題に対する他のアプローチを検討する必要があります。ファイル内の前のポイントに戻るという特定の問題については、この目標に対処するメソッドをjava.io.FileReader継承するように見えます。残念ながら、返品します。mark()reset()markSupported()false

または、をサポートします。以下のプログラムは、効果を示す を出力します。BufferedReader mark()true

package cli;

import java.io.BufferedReader;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStreamReader;

public class FileReaderTest {

    public static void main(String[] args) {
        try {
            BufferedReader in = new BufferedReader(new InputStreamReader(
                new FileInputStream("src/cli/FileReaderTest.java")));
            in.mark(1);
            int i1 = in.read(); in.read(); in.read();
            in.reset();
            int i2 = in.read();
            System.out.println(i1 == i2);
        } catch (IOException e) {
            e.printStackTrace(System.err);
        }
    }
}
于 2010-02-09T06:24:01.267 に答える
0

ファイル 2 ファイル リーダーを再初期化するだけでリセットできると思います。

于 2014-01-23T16:20:15.550 に答える
0

前述のように、より優れたアルゴリズムがあります - これらを調査してください

余談:

FileReader はマークとリセットを実装していないため、trushgod のコメントは不正確です。これのバージョンを (RandomAccessFile などを使用して) 実装するか、BufferedReader でラップする必要があります。ただし、後者は、マークを付けると、すべてをメモリにロードします

于 2010-03-19T19:51:02.453 に答える
0

簡単な質問です。あるオブジェクトをファイルの先頭に向けたままにして、別のオブジェクトでファイルをトラバースすることはできませんか? 次に、最後に到達したら、ファイル(ストリーム)の先頭にあるオブジェクトを指すだけです。C++にはファイルI/O(またはストリームI/O)を備えたそのようなメカニズムがあると思います

于 2010-03-19T20:04:06.553 に答える