파일당 하나씩 두 개의 정렬된 데이터 세트를 일치시키고 병합하려고 합니다. 각 파일에는 키 필드와 관련 값이라는 두 개의 열이 포함되어 있습니다. 생성된 출력에는 키 필드, 첫 번째 파일의 값(있는 경우) 및 두 번째 파일의 값(있는 경우)이라는 세 개의 열이 포함되어야 합니다. 일치하지 않는 데이터 행을 포함해야 합니다.
첫 번째 파일 "John"
apple,green
cherry,red
orange,orange
두 번째 파일 "Jane"
apple,red
banana,yellow
cherry,yellow
kiwi,green
원하는 결과
apple,green,red
banana,,yellow
cherry,red,yellow
kiwi,,green
orange,orange,
처음에는 이 일이 나에게 하찮은 일이라고 생각했다.join
LC_ALL=C join -j1 -a1 -a2 -t',' john jane
그러나 결과는 항상 -a1 -a2
두 번째 열에 일치하지 않는 값을 넣습니다.
apple,green,red
banana,yellow
cherry,red,yellow
kiwi,green
orange,orange
이상적으로는 결과 파일의 적절한 두 번째 또는 세 번째 열에 해당 값을 배치하여 일치하지 않는 값이 어떤 소스 파일에서 유래했는지 확인할 수 있어야 하지만 달성할 수 있는 간단한 방법을 알 수 없습니다. 유형 구성을 자세히 알아볼 필요 없이 이 작업을 수행할 수 있습니다 awk ... getline()
.
어떤 제안이 있으십니까?
답변1
당신이 원하는 -o auto
:
join -t, -j 1 -a 1 -a 2 -o auto john jane
~에서man join
:
-o FORMAT
순종하다
FORMAT
출력 라인을 구성할 때
︙만약FORMAT
키워드가 'auto
'인 경우 각 파일의 첫 번째 줄은 각 줄에 출력되는 필드 수를 결정합니다.
또는 더 잘 설명GNU Coreutils: 호출 추가 (링크를 클릭하시면 들어가실 수 있습니다.조인의 일반 옵션):
'
-o auto
'" " 키워드가 지정되면
auto
출력 형식은 각 파일의 첫 번째 줄에서 유추됩니다. 이는 기본 출력 형식과 동일하지만 행당 동일한 수의 필드가 출력되도록 보장합니다. 누락된 필드는 옵션으로 대체되고-e
중복 필드는 삭제됩니다.
% cat john
apple,green
cherry,red
orange,orange
% cat jane
apple,red
banana,yellow
cherry,yellow
kiwi,green
% join -t, -j 1 -a 1 -a 2 -o auto john jane
apple,green,red
banana,,yellow
cherry,red,yellow
kiwi,,green
orange,orange,
답변2
출력 형식을 명시적으로 지정할 수 있습니다.
LC_ALL=C join -o0,1.2,2.2 -j1 -a1 -a2 -t',' john jane
생산하다
apple,green,red
banana,,yellow
cherry,red,yellow
kiwi,,green
orange,orange,
여기서 중요한 점은 조인 필드를 출력 형식에서도 참조할 수 있다는 점입니다 0
. 이는 페어링할 수 없는 행의 컨텍스트에서 유용합니다.
답변3
이 명령은 거의 해당 작업을 수행합니다. 키가 file1에만 나타나면 후행 쉼표가 생략됩니다. 지금은 완전히 디버깅할 시간이 없습니다.
awk -F, 'BEGIN{OFS=","} FNR==NR{val[$1]=$2;next} {val[$1]=val[$1] "," $2}END{for (key in val) {print key, val[key]}}' john jane
산출:
apple,green,red
banana,,yellow
cherry,red,yellow
kiwi,,green
orange,orange
답변4
R 프로그래밍 언어 사용
두 개의 데이터 파일을 R REPL로 읽습니다.
> john <- read.csv("/Users/admin/john", header=FALSE, stringsAsFactors=FALSE)
> john
V1 V2
1 apple green
2 cherry red
3 orange orange
>
> jane <- read.csv("/Users/admin/jane", header=FALSE, stringsAsFactors=FALSE)
> jane
V1 V2
1 apple red
2 banana yellow
3 cherry yellow
4 kiwi green
R REPL에서 데이터 파일을 병합하려면 다음을 수행하십시오.
> merge(john, jane, by = c("V1"), all=TRUE)
V1 V2.x V2.y
1 apple green red
2 banana <NA> yellow
3 cherry red yellow
4 kiwi <NA> green
5 orange orange <NA>
>
파일로 출력( 사용 write.table
):
> write.table( merge(john, jane, by = c("V1"), all=TRUE), "john_jane.csv", sep=",", quote=F, row.names=F, col.names=F, na="")
생성된 파일("john_jane.csv"):
apple,green,red
banana,,yellow
cherry,red,yellow
kiwi,,green
orange,orange,
매개변수에서 볼 수 있듯이 write.table
<NA> 값은 를 사용하여 빈 문자열로 설정됩니다 na=""
. 추가 도움말을 보려면 R REPL의 프롬프트에 , 또는 ?getwd()
와 같은 물음표 앞에 명령을 입력하세요 ?setwd()
.?read.csv()
?merge()
[참고: R 설치 기간에 따라 stringsAsFactors=FALSE
모든 함수 호출에 매개변수를 포함하는 것이 중복될 수 있습니다.]read.csv()
https://www.r-project.org/
https://cran.r-project.org/index.html