파일이 있다고 가정해 보겠습니다.
uid=1(a) groups=cat,dog,hen
uid=2(b) groups=cat,hen
uid=3(c) groups=hen
uid=4(d) groups=dog,hen,buffalo,horse
내가 찾고 있어요:
cat a,b
dog a,d
hen a,b,c,d
buffalo d
horse d
목록 #1: 사용자 및 보조 그룹(사용자별)
목록 #2: 그룹 및 사용자(그룹에 속함)
답변1
awk -F "[= ,()]" '{
for(i=6;i<=NF;i++){
if(a[$i] != ""){
a[$i]=a[$i]","$3
}else{
a[$i]=$3
}
}
}
END{
for ( i in a){
print i,a[i]
}
}'
각 그룹 구성원으로 인덱싱된 배열을 만들고 uid
그룹 구성원이 행에서 발견되면 배열에 추가합니다. 첫 번째는 END
배열 인덱스와 배열의 값입니다.
답변2
#!/usr/bin/env perl
use strict;
use warnings;
use feature qw(say);
my %groups;
while ( my $line = readline *STDIN ) {
chomp $line;
if ( $line =~ m/\((?<user>[^)]+)\) groups=(?<groups>.+)/ ) {
for my $groupname ( split ',', $+{groups} ) {
push @{ $groups{$groupname} }, $+{user};
}
} else {
warn "NOTICE non-matching line $. - '$line'\n";
}
}
for my $groupname ( sort keys %groups ) {
say $groupname, ' ', join ',', @{ $groups{$groupname} };
}
이 버전은 배열 참조(사용자)의 해시(그룹)를 사용하고 입력 행과 일치하지 않을 때 경고합니다(데이터가 손상되었습니까? 어떻게 알 수 있습니까?).
답변3
그리고 perl
:
perl -lne '
if (/^uid=\d+\((.+)\) groups=(.*)/) {
push @{$u{$_}}, $1 for split /,/, $2;
}
END {
$" = ",";
print "$_ @{$u{$_}}" for keys %u;
}'