将一个文件中的用户名替换为另一文件输出中的用户名加公司

将一个文件中的用户名替换为另一文件输出中的用户名加公司

我有 2 个文本文件。一个是用户名列表以及他们在同一行工作的公司,但以制表符空格分隔。第二个是每周生成的报告的输出,其中包含更多信息。

目标是从每周报告中获取名称,并将其替换为用户名列表中的名称和公司。

用户名和公司列表在 UserList.txt 文件中看起来像这样,其中由制表符空格分隔。

Name1      Company 1
Name2      Company 2
Name3      Company 3
Name4      Company 4
Name5      Company 5

每周输出文件位于 Weekly.txt 文件中

测试.txt

我不知道如何查看第一个文本文件以获取名称和公司名称,并仅替换第二个文本文件中的该部分。

我正在寻找最终的输出,如下所示:

最终输出.txt

到目前为止,我找到了一种使用sed命令手动执行此操作的方法。这是我到目前为止所拥有的:

sed -r 's/Name1/Name1 Company 1/g;s/Name2/Name2 Company 2/g;s/Name3/Name3 Company 3/g;s/Name4/Name4 Company 4/g;s/Name5/Name5 Company 5/g'

这是可行的,但它不会读入另一个文件并提取最新信息。请记住,我正在使用 cygwin,这都是更大脚本的一部分。

答案1

使用join命令:

join -t $'\t' -1 1 -2 2 -o 2.1,1.1,1.2,2.3 \
    user_list.txt \
    <(sed -E 's/^(loginName:)\s+(\S+)\s+(.*)$/\1\t\2\t\3/' test.txt)

join-1 1将使用第一个文件中的第 1 列 ( ) 和第二个文件中的第 2 列 ( )连接两个表-2 2。它将按照 指定的顺序打印列-o

在问题的原始版本中,用户列表采用 XLSX 格式。在这种情况下:

join -t $'\t' -1 1 -2 2 -o 2.1,1.1,1.2,2.3 \
    <(xlsx2csv -d tab test.xlsx | tail -n +2) \
    <(sed -E 's/^(loginName:)\s+(\S+)\s+(.*)$/\1\t\2\t\3/' test.txt)

在 Debian 上,xlsx2csv以软件包 ( ) 的形式提供apt install xlsx2csvjoin是套餐的一部分coreutils

编辑:调整为使用制表符而不是逗号作为分隔符,用户列表以纯文本格式而不是 XLSX 格式显示。

答案2

一种解决方案是对用户文件中的每行进行替换。以下脚本将就地编辑 Weekly.txt:

prefix="loginName:\s*"
tail -n+2 UserList.txt | while read line; do
    name=$(printf "$line" | cut -f1)
    company=$(printf "$line" | cut -f2 | tr -d '\n')
    sed -i "s/^\($prefix\)$name/\1$name $company/g" Weekly.txt
done

为了提高效率,我们可以收集替换内容并执行 sed 一次:

prefix="loginName:\s*"
sedCommand=$(tail -n+2 UserList.txt | while read line; do
    name=$(printf "$line" | cut -f1)
    company=$(printf "$line" | cut -f2 | tr -d '\n')
    printf "s/^\($prefix\)$name/\1$name $company/g;"
done)
sed "$sedCommand" Weekly.txt > new_Weekly.txt

此版本保持Weekly.txt不变并将结果写入new_Weekly.txt.

相关内容