【问题标题】:Replace a string from a list with the next line from another list用另一个列表中的下一行替换列表中的字符串
【发布时间】:2018-08-21 18:47:30
【问题描述】:

我有 3 个文件。一个是食物和类别的列表:

                 food="rice"
                 product="cereal"
                 food="beans"
                 product="bean"
                 food="cake"
                 product="bakery"
                 food="lettuce"
                 product="leaves"

第二个是食物清单:

                 food="rice"
                 food="beans"
                 food="cake"
                 food="lettuce"

在第三个文件中,我有包含 /food 文件字符串的行(例如 /food="rice"),我需要将这些字符串替换为第一个文件中列出的相应产品。为了简化:在文件 3 上从文件 2 中找到字符串,并在文件 3 上用文件 1 的下一行替换。 我想也许是 grep 和 sed 的组合,但我不知道如何...... 第三个文件看起来像这样

>[food="rice"] [some other sutff] [calories=398]
Here is a recipe with rice
>[food="beans"] [some other sutff] [calories=250]
Here is a recipe with beans
>[food="cake"] [some other sutff] [calories=100]
Here is a recipe for cake
>[food="lettuce"] [some other sutff] [calories=02]
Why would you need a recipe for lettuce?

我需要它看起来像......

 >[product="cereal"] [some other sutff] [calories=398]
 Here is a recipe with rice
 >[product="bean"] [some other sutff] [calories=250]
 Here is a recipe with beans
 >[product="bakery" [some other sutff] [calories=100]
 Here is a recipe for cake
 >[product="leaves"] [some other sutff] [calories=02]
 Why would you need a recipe for lettuce?

【问题讨论】:

  • 能否请您也发布第三个文件的示例以及预期的输出示例,然后让我们知道?
  • 我刚刚更新了帖子
  • 请避免"Give me the codez" 问题。而是显示您正在处理的脚本并说明问题所在。另见How much research effort is expected of Stack Overflow users?
  • @SilviaJusti,还是不清楚,请详细说明一下?
  • 为什么你需要只包含食物的第二个文件?

标签: linux awk sed grep


【解决方案1】:

这是使用sed的解决方案:

sed -f <(sed 'N;s/\n/\//;s/^/s\//;s/$/\//' one) three

如果第一个文件的每一行都真的以空格开头,那就变成了

sed -f <(sed 'N;s/ *//g;s/\n/\//;s/^/s\//;s/$/\//' one ) three

【讨论】:

  • 非常感谢您纠正我的错误。我已经修改了我的答案。
【解决方案2】:

这是sed/awk 组合

$ sed -f <(awk '     {gsub(/ /,"")} 
             NR==FNR {if(/food/) k=$0; if(/product/) a[k]=$0; next} 
             $0 in a {print "s/" $0 "/" a[$0] "/g"}' f1 f2) f3

>[product="cereal"] [some other sutff] [calories=398]
Here is a recipe with rice
>[product="bean"] [some other sutff] [calories=250]
Here is a recipe with beans
>[product="bakery"] [some other sutff] [calories=100]
Here is a recipe for cake
>[product="leaves"] [some other sutff] [calories=02]
Why would you need a recipe for lettuce?

【讨论】:

  • 差不多吧,我只希望>[food="rice"]改成>[food="cereal"],下一行应该保持原样,还是说rice...需要完全匹配,不仅与类别匹配,还与字符串的其余部分匹配
  • 已修复,只要没有空白就应该可以工作,否则您需要从令牌中修剪它们。
【解决方案3】:

我看不到 file2 的用途。

$ cat tst.awk
BEGIN { FS="[][]" }
NR==FNR {
    gsub(/^[[:space:]]+|[[:space:]]+$/,"")
    if (NR%2) { food = $0 }
    else { map[food] = $0 }
    next
}
{
    sub(/\[[^][]+/,"["map[$2])
    print
}

$ awk -f tst.awk file1 file3
>[product="cereal"] [some other sutff] [calories=398]
Here is a recipe with rice
>[product="bean"] [some other sutff] [calories=250]
Here is a recipe with beans
>[product="bakery"] [some other sutff] [calories=100]
Here is a recipe for cake
>[product="leaves"] [some other sutff] [calories=02]
Why would you need a recipe for lettuce?

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2012-08-18
    • 2019-01-12
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-07-20
    • 1970-01-01
    相关资源
    最近更新 更多