2012-01-02 2 views
1

기본적인 Java 문제는 다음과 같습니다. 청크별로 파일을 읽은 다음 청크의 순서를 반대로 변경 한 다음 새 파일에 기록해야합니다. 내 첫 (순진한) 시도는 다음 접근 방식을 따랐습니다.파일의 역 청크

  1. 파일에서 청크 읽기.
  2. 반복 새 파일에 대한 모든 덩어리
  3. 쓰기 결과 목록의 결과 목록의 앞에 한 번에 청크
  4. 푸시 바이트 하나의 바이트를 역
  5. .

기본적으로 이것은 매우 어리 석고 느린 방법으로 문제를 해결하지만 찾고자하는 올바른 출력을 생성합니다. 상황을 개선하려고,이 알고리즘 변경 :

  1. 배열 목록의 전면에 파일
  2. 푸시 청크에서 덩어리를 읽어들이는 모든 덩어리
  3. 의 foreach에 대한
  4. 반복 청크, 새 파일에 쓰기

내 생각에 똑같은 결과물이 나온다. 그것을 제외하고 나는 아주 혼란 ​​스럽다. 결과 파일의 첫 번째 청크는 두 방법 모두와 일치하지만 나머지 파일은 완전히 다릅니다.

FileInputStream in; 
FileOutputStream out, out2; 

Byte[] t = new Byte[0]; 
LinkedList<Byte> reversed_data = new LinkedList<Byte>(); 
byte[] data = new byte[bufferSize]; 
LinkedList<byte[]> revd2 = new LinkedList<byte[]>(); 

try { 
in = new FileInputStream(infile); 
out = new FileOutputStream(outfile1); 
out2 = new FileOutputStream(outfile2); 
} catch (FileNotFoundException e) { 
    e.printStackTrace(); 
    return; 
} 
while(in.read(data) != -1) 
{ 
    revd2.addFirst(data); 
    byte[] revd = reverse(data); 
    for (byte b : revd) 
    { 
     reversed_data.addFirst(b); 
    } 
} 
for (Byte b : reversed_data) 
{ 
    out.write(b); 
} 
for (byte[] b : revd2) 
{ 
    out2.write(b); 
} 

http://pastie.org/3113665에서 당신은 완벽한 예제 프로그램을 볼 수 있습니다 (긴 내 디버깅 시도 포함) : 여기

내가 사용하고있는 자바 코드의 고기입니다. 단순함을 위해 나는 모든 청크가 같은 크기가 될 수 있도록 파일의 크기를 균등하게 나누는 bufferSize를 사용하고 있지만 현실 세계에서는 그렇지 않습니다. 내 질문은 이러한 두 가지 방법으로 동일한 출력을 생성하지 않는 이유는 무엇입니까? 나는 그것을 마실 수 없기 때문에 나를 미치게 만든다.

+1

숙제가 맞습니까? 나는 단지 문제의 더 큰 맥락이 무엇인지 궁금 할 뿐이다. – bobbymcr

+0

첫 번째 아기가 신호 처리를 시작합니다. 데이터는 PCM 스트림입니다. – Segfault

+1

그래서 혼란 스럽네요. 파일에서 모든 바이트를 역순으로 할당하는 것입니까, 아니면 청크의 순서를 바꾸는 것입니까? –

답변

1

이전에 읽은 데이터를 계속해서 덮어 쓰는 중입니다.

while(in.read(data) != -1) 
{ 
    revd2.addFirst(data); 
    // ignore byte-wise stuff 
} 

당신은 목록 revd2에 반복적으로 동일한 개체를 추가하고, 각각의리스트 노드는 마침내 마지막 read의 결과로 가득 data에 대한 참조를 포함합니다. 나는 이것을 revd2.addFirst(data.clone())으로 바꾸는 것이 좋습니다.

+0

감사합니다, 그것은 나를 미치게했습니다. 나는 그것을 보지 못했다고 믿을 수 없다. – Segfault

+0

물론'data.clone()'은 원래의 순서대로 존재하기 때문에'data.clone()'을 중복시키는 방식으로 제안한 것을해야 할 것입니다. ;) –

+1

@ PeterLawrey 아니요, 목표는 각 청크에서 바이트 순서를 유지하면서 청크의 순서를 뒤집는 것이 었습니다. 원래의 byte-wise 코드는 각 청크를 '역방향'당 한 번씩, 그리고 큰 바이트의 fron으로 각 바이트를 밀어서 두 번씩 역순으로 바꾼다. –

0

내 생각 엔 당신이 이렇게 반전 된 복사본이 목록의 시작에 추가됩니다에 대한

revd2.addFirst(data); 
byte[] revd = reverse(data); 

을 변경할 수 있습니다.

byte[] revd = reverse(data); 
revd2.addFirst(revd); 
+0

@MikeNakis 후반부가 제 대답입니다. 아마도 나중에 추가했습니다. ?? –

+0

첫 번째 방법은 청크를 두 번 뒤집습니다. 먼저 청크는 reverseie (이 함수는 pastie.org에서 볼 수 있습니다)에서 역전 처리 한 다음 각 바이트를 결과 목록의 앞쪽으로 밀어 넣으면 다시 뒤집습니다. . – Segfault

+0

@Segfault 나는 당신이 그것을 두 가지 다른 방식으로하고 있다는 것을 이해합니다. 'out2'에 대한 한 가지 방법과 'out2'에 대한 두 번째 방법 –