2010-08-19 1 views
2

이것은 꽤 초보자 질문 일지 모르지만, 특정 텍스트 파일을 처리하고 그 내용을 바이너리 파일로 덤프해야하고 어떻게해야할지 모르겠다. 필자는 펄을 사용하기로 결정했지만 필자의 펄 스킬은 매우 낮다. 아마 C++로 작성 했어야하지만, 이것은 perl을위한 멋지고 쉬운 작업처럼 보입니다. 그래서 새로운 것을 배울 필요가 없을까요?) 텍스트 파일 형식으로 수천 줄의가 있습니다Perl을 사용하여 지정된 형식의 데이터를 이진 파일에 쓰는 방법은 무엇입니까?

2A02FC42 4

당신은 (길이가 항상 8)과 일반 숫자 16 진수로 볼 수 있습니다. 지금은 (16 진수 편집기로 볼 때 다음과 같아야합니다)이 형식의 바이너리 파일로 모든 라인을 덤프해야합니다

42FC022A00000004

더 많은 예제를 분명히 그래서 :

70726F67 36 ->676F727000000024
6A656374 471 ->7463656A000001D7

입력 파일을 구문 분석의 부분은 쉽게,하지만 난 이진 파일로이 작성해야 두 번째 부분에 붙어있어. 이 방법으로 데이터를 포맷하는 방법이나 바이너리 모드로 출력하는 방법을 알지 못합니다. 누군가 나를 도와 줄 수 있습니까?

감사합니다.

EDIT : LE 시스템에서 endiannes - im을 잊어 버렸습니다. 예제를 업데이트했습니다.

+1

http://perldoc.perl.org/functions/pack.html –

답변

6

사용 pack :

#! /usr/bin/perl 

use warnings; 
use strict; 

# demo only  
*ARGV = *DATA; 

while (<>) { 
    my($a,$b) = split; 
    $a = join "", reverse $a =~ /(..)/g; 
    $b = sprintf "%08x", $b; 

    print pack "H*" => $a . $b; 
} 

__DATA__ 
2A02FC42 4 
70726F67 36 
6A656374 471 

샘플 실행 :

$ ./prog.pl | od -t x1 
0000000 42 fc 02 2a 00 00 00 04 67 6f 72 70 00 00 00 24 
0000020 74 63 65 6a 00 00 01 d7 
0000030
+0

감사합니다. 이것은 매력처럼 작동합니다! – PeterK

+0

@ 페터럴 환영합니다! 도움이 돼서 기쁩니다. –

+0

최상의 이식성을 위해서 출력 스트림을 위해 바이너리 모드를 토글해야한다 :'binmode (STD0UT)' – dolmen

0

표준 방식은 pack을 사용하는 것입니다. 텍스트 파일에서 읽은 데이터가 이미 숫자 (16 진수 1 포함)로 변환되고 vars $x$y에 저장되어 있다고 가정 해 봅시다. 서로 다른 바이트 순서가 필요한 경우 그럼 당신은

print OUTFILE pack("NN", $x, $y); 

같은 것을해야한다, 당신은 NN에서 다른 템플릿을 사용하여 자세한 내용은 perldoc -f pack을 볼 수있을 것이다.

+0

맨손으로 파일 핸들을 사용하지 마십시오. 'print $ outfile ....'이 더 좋습니다. – gvkv

1

내 버전 (테스트) :

my $fout; 
if (! open($fout, ">/tmp/deleteme.bin")) { 
    die("Failed to open /tmp/deleteme.bin: $!"); 
} 
binmode($fout); 

while (<DATA>) { 
    my ($left, $right) = split(/\s+/s, $_); 

    my $output = pack("VN", hex($left), int($right)); 
    printf(
     STDERR 
     " note, %8X %d -> " . ("%02X" x 8) . "\n", 
     hex($left), $right, 
     map { $_ } unpack("C8", $output) 
    ); 

    print($fout $output); 
} 
close($fout); 

__DATA__ 
70726F67 36 -> 676F727000000024 
6A656374 471 -> 7463656A000001D7 

출력 :

note, 70726F67 36 -> 676F727000000024 
note, 6A656374 471 -> 7463656A000001D7 
,536,913,632 10