【问题标题】:Select rows after certain condition在特定条件后选择行
【发布时间】:2018-08-21 18:52:10
【问题描述】:

选择找到的最大最小值之后的行

输入文件

22 101 5
23 102 5
24 103 5
25 104 23
26 105 25
27 106 21
28 107 20
29 108 8
30 109 6
31 110 7

为了找出我的问题,我尝试减去第 3 列并打印第 4 列中找到的最小值之后的行。在这种情况下,在第 7 行之后

awk '{$4 = $3 - prev3; prev3 = $3; print $0}' file

22 101 5 
23 102 5 0
24 103 5 0
25 104 2 18
26 105 2 2
27 106 2 -4
28 107 2 -1
29 108 8 -12
30 109 6 -2
31 110 7 1

期望的输出

29 108 8
30 109 6
31 110 7

我相信有更好更简单的方法来获得相同的输出。

提前致谢

【问题讨论】:

  • 你能澄清你的问题描述吗?是否必须在找到最小值之后? valor 是错字吗?你的意思是 value,还是一个特定的术语(如果是,请解释)。第一行和第二行在这里有什么意义或用处吗?
  • 不清楚,您在第 4 列中提到逻辑 + 加法,但您正在写减法?也不清楚你在说哪个最大值和最小值?第 4 列还是第 3 列?请使用正确的示例编辑您的帖子,然后回复我们。
  • 如果只有两行会发生什么,例如:22 101 5 <newline> 23 102 7?应该打印两行还是只打印最后一行(“0th”行的默认值是多少)?
  • 鉴于输出和第四列中的值,我猜“最大最小 valor”是指两个连续行之间差异的最大 值。但这必须由 OP 澄清。

标签: awk


【解决方案1】:

同一个文件需要处理两次:

  1. 找出最小值的行号
  2. 打印该行及其后的行

像这样:

awk 'NR==FNR{v=$3-prev3;prev3=$3;if(NR==2||v<m){m=v;ln=NR};next}FNR>=ln' file file

解释:

# This condition is true as long as we process the file the first time
NR==FNR {

    # Your calculation
    v=$3-prev3
    prev3=$3

    # If NR==2, meaning in row 2 we initialize m and ln.
    # Otherwise check if v is the new minimum and set m and ln.
    if(NR==2 || v<m){
        # Set m and ln when v is the new minimum
        m=v
        ln=NR
    }

    next # Skip the conditional below
}

# This condition will be only evaluated when we parse the file
# the second time. (because of the "next" statement above)

# When the line number is greater or equal than "ln" print it.
# (print is the default action)
FNR>=ln

【讨论】:

  • 谢谢 :) ... 执行 OP 的内容时更容易理解(并将 + 更改为 -
  • 如果/当所有 $3 值都大于它们的前一个值时,这将失败。尝试使用 $3 为 2、3、4 等的输入。当 m 为空时,您需要添加一个条件来填充 m 和 ln,而不仅仅是当 m 小于 v 时,否则您将依赖于v 在某些时候变为负数导致第一次设置 m。这就像任何其他最小/最大值计算一样 - 您得到将初始值用作最小值/最大值。
  • @EdMorton 谢谢!
  • 没问题,你不需要初始化 m 和 ln - awk 会为你做这件事,并且比使用零或空值更好,这样你就可以区分第一次使用和具体数值。只需摆脱有关初始化 m 和 ln 的所有内容并将 if(v&lt;m){ 更改为 if (NR==2 || v&lt;m) { (假设 OP 不想将前 3 美元与 0 进行比较),您就可以开始了!
  • 听起来好多了。将改变这一点(稍后,atm 工作)
猜你喜欢
  • 1970-01-01
  • 2012-10-03
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2022-11-28
  • 1970-01-01
相关资源
最近更新 更多