假设我有一个文件:
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;
}'