从命令行提取大量 csv 文件的一部分

从命令行提取大量 csv 文件的一部分

我想读取大型 csv 文件的第 n 行和第 m 行以及第 p 列和第 q 列之间的部分。有没有一种简单的方法可以用 shell 轻松完成此操作?(是否有我应该阅读文档的命令?否则,我将编写一个 python 脚本)

答案1

我有一个经过调整的脚本((N+1)q 部分是个好主意!)感谢@chronitis 的评论和所以回答

#! /bin/bash 
#
N=10
M=20
P=2
Q=3
sed -n "$N,${M}p; $((M+1))q" $1 | cut -d, -f$P-$Q

将文件另存为例如cut_csv,使其可执行并使用

cut_csv file

它可以通过接受 N、M、P、Q 参数作为输入等变得更加奇特,但我很少使用它,所以我通常只是编辑文件。

怎么运行的

主命令如下(假设 N=10、M=20、P=2、Q=3);shell 替换变量,最后一行将变为:(1)

sed -n "10,20p ; 21q" file | cut -d, -f2-3

让我们从第一个命令开始:

sed -n "10,20p ; 21q" file 

man sed这将在无打印模式( )下调用 sed(流编辑器, )-n并对文件执行以下命令:

  1. 打印(p)10 到 20 之间的行(这是10,20p部分)
  2. q读取第 21 行时退出( ) 21q,以便丢弃文件的其余部分

sed 的输出通过管道( |)传输到cut

cut -d, -f2-3

此命令 ( man cut) 选择一行的字段(并对每一行重复此操作)。在本例中,我告诉它字段(列)之间的分隔符是逗号 ( -d,),并打印出 2 到 3 之间的列。

作为另一个更复杂的例子,我经常使用这个:

sed -n "1p; 10,14p; 21q" data.csv | cut -d, -f1,4-8

这将选择第 1 行(其中有标题 :-))和第 10 到第 14 行(5 行);然后选择第 1 列(我的数据中的时间...)和第 4 到第 8 列。一旦掌握它,它就真的很强大。

(1)查看 shell 正在做什么的一个好方法是将第一行(称为舍邦) 像那样:

#! /bin/bash -xv

shell 现在将打印它读取的每个命​​令以及替换的结果:

(0)asus-rmano: part_of_csv.sh p20dedo.csv
#! /bin/bash -xv
#
N=10
+ N=10
M=20
+ M=20
P=2
+ P=2
Q=3
+ Q=3
sed -n "$N,${M}p; $((M+1))q" $1 | cut -d, -f$P-$Q
+ cut -d, -f2-3
+ sed -n '10,20p; 21q' p20dedo.csv
16:05:49,000
16:05:51,000
[...]

答案2

您可以使用管道将 awk 和 sed 结合起来

sed -n '10,50p' file.csv | awk -F ';' '{print $3 $4}'

10 和 50 是行。

-F';'是字段分隔符。(在我的示例中是分号)

$3 和 $4 是需要显示的字段。

答案3

以下脚本使用headtail能够打印.csv通过行号和列号过滤的文件的一部分。

#!/bin/bash
m="$2"
n="$3"
s="$4"
t="$5"
head -n "$n" "$1" | tail -n +"$m" | cut -d, -f "$s"-"$t"

将上述脚本保存为csv_view.sh并使其可执行。

chmod +x csv_view.sh

在哪里,

m=row number where to begin
n=row number where to end
n=column number where to begin
n=column number where to end

如何使用

./csv_view.sh mycsvfile.csv 11 32 4 7

它将打印第 11 至 32 行和第 4 至 7 列mycsvfile.csv

相关内容