稳健地分割包含噪声数据的 csv 文件

Evg*_*sky 5 command-line grep csv split

假设我有一个包含这些列的 csv 文件:

timestamp,cpu,memory
Run Code Online (Sandbox Code Playgroud)

实际数据形状的一个例子是这个图表:

cpu/mem csv 数据作为图表

以这种方式将数据可视化,人眼很容易分辨出 4 个 CPU 密集型活动中任何一个的开始和结束位置。

什么是一种简单的方法,使用标准的 unix cmd 行工具,理想情况下不诉诸Roctave等,仅“grep”文件的 8 行,这些行表示这 4 个活动的开始和结束,基于“cpu”列?

显然这有点模糊,并且数据中存在噪声,但是任何给我 8 行接近开始/结束的解决方案都值得赞赏。

csv 文件的简短摘录,仅显示了这 4 次活动爆发中的第一次:

10:44:21.310,0,53567488
10:44:22.310,1.56257,53575680
10:44:23.326,0,53854208
10:44:24.325,34.3761,57405440
10:44:25.325,73.43985,61747200
10:44:26.325,3.1251,69459968
10:44:27.325,0,69459968
10:44:28.325,0,69459968
10:44:29.325,65.6271,74756096
10:44:30.325,53.1267,77783040
...
10:50:56.450,35.93865,142700544
10:50:57.450,10.93785,142897152
10:50:58.450,1.56255,142897152
10:50:59.450,0,142897152
10:51:00.450,0,142897152
10:51:01.450,0,142897152
Run Code Online (Sandbox Code Playgroud)

理想情况下,这将导致以下 2 行。

10:44:24.325,34.3761,57405440
10:50:58.450,1.56255,142897152
Run Code Online (Sandbox Code Playgroud)

但是,由于在10:44:26.325和之间的几秒钟内没有 cpu 活动10:44:28.325,我不希望答案那么聪明并且做一些类似于“平滑”数据的事情。因此,如果像上面这样的 csv 片段会产生以下 4 行,那就足够了。

10:44:24.325,34.3761,57405440
10:44:26.325,3.1251,69459968
10:44:29.325,65.6271,74756096
10:50:58.450,1.56255,142897152
Run Code Online (Sandbox Code Playgroud)

jor*_*anm 5

一种方法是使用awk. 您可以设置一个阈值来获取阈值被命中的第一行和它低于的最后一行。像这样的事情可能会奏效:

awk -F, -vthreshold_up=20 -vthreshold_down=10 'BEGIN {
                          cur = "gt";
                        } 
                        {
                          if (cur == "gt" && $2 > threshold_up) {
                            print;
                            cur = "lt";
                          } else if (cur = "lt" && $2 < threshold_down) {
                            print;
                            cur = "gt";
                          }
                        }' file.csv
Run Code Online (Sandbox Code Playgroud)