我有一个~23000行的SQL转储,其中包含几个数据库的数据价值。我需要提取这个文件的某个部分(即单个数据库的数据),并将其放在一个新文件中。我知道我想要的数据的开始行号和结束行号。

谁知道一个Unix命令(或一系列命令)可以从文件中提取16224到16482行之间的所有行,然后将它们重定向到一个新文件中?


当前回答

站在拳击手的肩膀上,我喜欢这样:

sed -n '<first line>,$p;<last line>q' input

e.g.

sed -n '16224,$p;16482q' input

$表示“最后一行”,因此第一个命令使sed打印从第16224行开始的所有行,第二个命令使sed在打印第16428行之后退出。(在boxxar的解决方案中,为q范围添加1似乎没有必要。)

我喜欢这个变体,因为我不需要两次指定结束行号。而且我认为使用$不会对性能产生不利影响。

其他回答

使用head/tail非常简单:

head -16482 in.sql | tail -258 > out.sql

使用sed:

sed -n '16224,16482p' in.sql > out.sql

使用awk:

awk 'NR>=16224&&NR<=16482' in.sql > out.sql

也许,你会给这个简陋的脚本一个机会;-)

#!/usr/bin/bash

# Usage:
#   body n m|-m

from=$1
to=$2

if [ $to -gt 0 ]; then
# count $from the begin of the file $to selected line
    awk "NR >= $from && NR <= $to {print}"
else
# count $from the begin of the file skipping tailing $to lines
    awk '
    BEGIN   {lines=0; from='$from'; to='$to'}
            {++lines}
    NR >= $from {line[lines]=$0}
    END     {for (i = from; i < lines + to + 1; i++) {
                print line[i]
            }
    }'
fi

输出:

$ seq 20 | ./body.sh 5 15
5
6
7
8
9
10
11
12
13
14
15

$ seq 20 | ./body.sh 5 -5
5
6
7
8
9
10
11
12
13
14
15

awk还有另一种方法:

awk 'NR==16224, NR==16482' file

如果文件很大,最好在读取最后一行之后退出。这样,它就不会不必要地读取以下行:

awk 'NR==16224, NR==16482-1; NR==16482 {print; exit}' file

awk 'NR==16224, NR==16482; NR==16482 {exit}' file

我想从一个使用变量的脚本中做同样的事情,并通过在$变量周围加上引号来分隔变量名和p来实现:

sed -n "$first","$count"p imagelist.txt >"$imageblock"

我想把一个列表分成不同的文件夹,找到最初的问题和答案,这是一个有用的步骤。(分裂命令不是旧操作系统上的选项,我必须将代码移植到)。

我会用:

awk 'FNR >= 16224 && FNR <= 16482' my_file > extracted.txt

FNR包含从文件中读取的行的记录(行)号。