【问题标题】:Replace the first field with values from a mapping用映射中的值替换第一个字段
【发布时间】:2021-08-08 14:26:07
【问题描述】:

我在 txt 文件中有一些数据(基本上是边界框注释)(空格分隔)

我想用一些其他字符替换多次出现的特定字符。例如

0 0.649489 0.666668 0.0625 0.260877
1 0.89485 0.445085 0.0428084 0.084259
1 0.80625 0.508509 0.0469892 0.005556
2 0.529068 0.0906668 0.0582908 0.0954804
2 0.565625 0.0268509 0.0040625 0.0546296 

我可能不得不把它改成类似的东西

2 0.649489 0.666668 0.0625 0.260877
4 0.89485 0.445085 0.0428084 0.084259
4 0.80625 0.508509 0.0469892 0.005556
7 0.529068 0.0906668 0.0582908 0.0954804
7 0.565625 0.0268509 0.0040625 0.0546296  

这应该同时发生在所有元素仅在第一列中(不是一个在另一个替换之后,因为这会错误地索引它)

我基本上会有一个映射{old_class_1:new_class_1,old_class_2:new_class_2,old_class_3:new_class_3}等等......

我查看了帖子 here,但它不适用于我的情况,因为这些答案中描述的方法会将所有值更改为最后一个替换。

我也研究了这个post,但不确定这里的答案是否适用于我的案例,因为我将有大约 25 个类,因此索引(第一列的值)可以从0-24

我知道这可能可以在 python 中通过逐行读取每个文件并进行替换来完成,只是想知道是否有更快的方法

任何帮助将不胜感激。谢谢!

【问题讨论】:

  • 这对 awk 来说并不难。你试过什么?
  • 我并没有真正尝试使用awk,因为我不确定如何继续,我编辑了问题(不一定必须以 1 为增量)

标签: linux string sed replace syntax


【解决方案1】:

下面是一个简单示例,说明如何将第一列中的标签映射到不同的标签。

这将映射指定为变量;您同样可以在文件中指定它,或者完全指定它。主要考虑因素是您需要有明确的分隔符,并使用一种对 Awk 来说并非难以解析的格式。

awk 'BEGIN { n = split("0:2 1:4 2:7", m);
    for(i=1; i<=n; ++i) { split(m[i], p); map[p[1]] = p[2] } }
$1 in map { $1 = map[$1] }1' file

BEGIN 字段可以简化,但我想让它易于更新;现在您所要做的就是更新字符串,它是第一个 split 的第一个参数,以指定不同的映射。我们花费大量临时变量将值解析为关联数组map,然后主脚本将使用该数组。

最后的1 不是错字; “无条件打印每一行”是一个标准的 Awk 习语。

【讨论】:

    猜你喜欢
    • 2013-11-16
    • 2020-05-13
    • 2021-09-23
    • 2021-12-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多