2017-11-12 18 views
-3

ファイル「A」からバイトを読み込もうとしています。私は位置を求めるためにRandomAccessFileを使用しています。そして、 "y"バイトを読み込む必要があります。(JAVA)ファイルから「バッファ」バイト(または「y」バッファ)を読み込みます。

私は4096バイトのバッファを持っていて、 "y"が4096の倍数でないならば、私はもっと多くのバイトを読みます。

バッファを1バイトに設定すると、問題なく読み書きできます(ただし、遅すぎます)。

私が現時点で持っているコードは次のとおりです。

public void extractFile(int pos) { 
    try { 
     RandomAccessFile raf = new RandomAccessFile(this.archive, "r"); 

     /* Trying to read */ 
     raf.seek(arquivos.get(pos).getPosicaoInicio()); 
     ByteArrayOutputStream byteOutput = new ByteArrayOutputStream(); 
     byte[] buf = new byte[1]; // With 1 I can read, because every "y" is multiple of 1 
     byte[] bytes; 
     while (byteOutput.size() < arquivos.get(pos).getTamanho()) { 
      byteOutput.write(buf, 0, raf.read(buf)); 
     } 
     bytes = byteOutput.toByteArray(); 
     byteOutput.close(); 
     raf.close(); 

     /* Writing */ 
     File futuroArquivo = new File(arquivos.get(pos).getNome()); 
     FileOutputStream fos = new FileOutputStream(futuroArquivo); 
     fos.write(bytes); 
     fos.flush(); 
     fos.close(); 

    } catch (IOException ex) { 

    } 
} 

PS: "arquivos.get(POS).getTamanho()" 私の "Y" である

PS 2:私ができます「y」バイトの後ろにあるファイル全体を読む、他にもあるものがある

+1

['RandomAccessFile.read(byte [] buffer、int offset、int length)']を使用したことがありますか?](https://docs.oracle.com/javase/8/docs/api/java/io/RandomAccessFile .html#read-byte:A-int-int-)? – EJP

+0

ありがとうございます!それが本当に私を助けました。私は他の何かが必要でしたが、これは私の目を開いたものです。 –

答えて

1

バッファーはゼロ以上の任意のサイズにすることができ、ByteArrayOutputStreamは文字どおり時間の無駄です。そしてスペース。 read()もバッファをいっぱいにしていると仮定しています。それを書くためのより良い方法は、次のようになります。

RandomAccessFile raf = new RandomAccessFile(this.archive, "r"); 

/* Trying to read */ 
raf.seek(arquivos.get(pos).getPosicaoInicio()); 
byte[] buf = new byte[8192]; // or more, whatever you like really 

/* Writing */ 
File futuroArquivo = new File(arquivos.get(pos).getNome()); 
FileOutputStream fos = new FileOutputStream(futuroArquivo); 
int count; 
long rest = arquivos.get(pos).getTamanho(); 
while (rest > 0 && (count = raf.read(buf, 0, (int)Math.min(buf.length, rest))) > 0) 
{ 
    fos.write(buf, 0, count); 
    rest -= count; 
} 
fos.close(); 
raf.close(); 

私も代わりRandomAccessFileの、このためFileInputStream周りBufferedInputStreamを使用して検討します。あなたは本当にランダムアクセスをしているわけではなく、最初のシークまたはスキップだけです。

+0

意図を明確にするため、 'rest> 0 &&'を 'while'条件に追加するべきだと思います。 +1に関係なく。 – Andreas

+0

@アンドレアス合意。 'rest == 0'のときに' read() 'に頼ってゼロを返すつもりはありませんでした。 – EJP

0

EJPのコメントで、私はそれを解決することができました。私は少し余分なプロセスが必要でしたが、少なくとも私はそれを作った。

 long rest = arquivos.get(pos).getTamanho(); 
     while (rest > 4096) { 
      rest -= 4096; 
      byteOutput.write(buf, 0, raf.read(buf)); 
     } 
     byteOutput.write(buf, 0, raf.read(buf, 0, (int) rest)); 

PS:BUFのサイズが4096の代わりにする必要がある解決策は、AUXILIARのVAR(Iが「休止」と呼ばれ、単にコードの他の部分が同じで、whileループを変更する)必要があります1

関連する問題