설명하다:

설명하다:

다음과 같은 파일이 있습니다.

 S123456789^ABC|00||00||ZZ|MW00021C|ZZ|207RI0200X~LX|1~SV2|6666|FG>FG997|879.5|UN|4~DTP|472|D8|20150213~REF|6R|JHYU0003707988-1~LIN||N4|67202004164~LX|2~SV2|1234|FG>BP990|879.5|UN|12~DTP|472|D8|20170413~REF|6R|ABCD0003707988-1~LIN||N4|67202004908~

1아래와 같이 다음 항목 LX, 다음 FG997항목을 추출한 다음 LIN||N4 옆에 있는 67202004164로 추출하고 다시 다음 항목으로 추출 하고 싶습니다 .SV2|****|HC> ,879.54UN,20150213DTP|472|D82LX

UNIX를 사용하여 이를 달성하도록 도와줄 수 있는 사람이 있습니까?

이런 방식으로 구문 분석해야 하는 대용량 파일이 많이 있습니다.

답변1

파일의 모든 행이 동일한 구조를 갖는 경우 아래와 같이 awk를 사용할 수 있습니다.

$ awk -F"[|^~>]" -v OFS="," '{for (i=1;i<=NF;i++) print "Field",i,"---value:",$i}' <<<"$a"

#Output will be like:
Field,1,---value:,S123456789
Field,2,---value:,ABC
Field,3,---value:,00
Field,4,---value:,
Field,5,---value:,00
Field,6,---value:,
Field,7,---value:,ZZ
Field,8,---value:,MW00021C
Field,9,---value:,ZZ
Field,10,---value:,207RI0200X
Field,11,---value:,LX
Field,12,---value:,1
Field,13,---value:,SV2
Field,14,---value:,6666
Field,15,---value:,FG
Field,16,---value:,FG997
##More fields here - goes up to 51 ##

awk는 -F구분 기호(입력 필드 구분 기호)를 정의하며 여러 문자일 수 있습니다.
위의 예에서는 chars |, ^, ~>구분 기호로 사용하여 awk가 행을 더 많은 부분으로 분할하도록 합니다.
더 많은 구분 기호를 추가하여 awk가 필드를 더 많은 부분으로 분할하도록 할 수 있습니다.
추신: 내 예의 변수 $a에는 질문 텍스트가 포함되어 있습니다.

원하는 필드를 식별했으므로 다음과 같은 스크립트를 작성하여 원하는 필드를 인쇄할 수 있습니다.

$ awk -F"[|^~>]" -v OFS="," '{print $1,$12,$16,etc}' <<<"$a"

OFS는 print가 필드를 인쇄하는 데 사용할 출력 구분 기호를 정의합니다.

awk에서 인쇄하는 경우 다음을 참고하세요.
* 이와 같은 내용을 인쇄할 때 '{print $1,$2}'두 필드는 OFS(위 예에서는 쉼표)로 구분됩니다. --> field1,field2
* awk와 같은 내용을 인쇄하면 '{print $1 $2}'두 필드가 인쇄됩니다. 필드는 연결됩니다 - 하나 차례로, 분리 없이 -->field1field2

답변2

이런 일은 쉽습니다 Perl.

perl -lne '
   BEGIN{ $SKIP = qr/(?:[^|]+[|])/;  $, = ","; }

   print map { s/[~].*[|]/,/;  y/|/,/;  s/,?$//r; }
     /
        ^[^^]+
        | (?: LX  [|] )              \K \d+
        | (?: SV2 [|] \d+ [|] FG[>] )\K     $SKIP{2}
        | (?: UN  [|] )              \K \d+ $SKIP{3} \d+
        | (?: LIN [|][|] $SKIP )     \K \d+
     /xg;

' yourfile

설명하다:

-l=> ORS=FS=\n -n=> dont print unless asked to -e=> 다음은 Perl코드입니다. $,=>OFS

BEGINblock은 파이프로 구분된 필드를 건너뛰는 정규식을 정의합니다. 이 정규식은 파이프로 구분된 2개의 필드(때로는 3개까지)를 건너뛰어야 할 때 여러 번 발생하기 때문에 can( box대신 읽 습니다). ability이렇게 하면 덜 무섭게 보입니다 regex.

/.../xg는 모든 일치 항목의 목록(\K 오른쪽에 나타나는 항목만)을 반환하고 map { ... }는 일부 처리를 수행하고 결과를 표준 출력으로 인쇄합니다.

산출

S123456789,1,FG997,879.5,4,20150213,67202004164,2,BP990,879.5,12,20170413,67202004908

관련 정보