shell脚本的使用---cut截取数据

linux之cut命令的用法

作者: 字体:[增加 减小] 类型:转载 时间:2013-10-03 我要评论

cut是一个选取命令,就是将一段数据经过分析,取出我们想要的。一般来说,选取信息通常是针对“行”来进行分析的,并不是整篇信息分析的

(1)其语法格式为:

cut  [-bn] [file] 或 cut [-c] [file]  或  cut [-df] [file]

使用说明

cut 命令从文件的每一行剪切字节、字符和字段并将这些字节、字符和字段写至标准输出。

如果不指定 File 参数,cut 命令将读取标准输入。必须指定 -b、-c 或 -f 标志之一。

主要参数

-b :以字节为单位进行分割。这些字节位置将忽略多字节字符边界,除非也指定了 -n 标志。

-c :以字符为单位进行分割。

-d :自定义分隔符,默认为制表符。

-f :与-d一起使用,指定显示哪个区域。

-n :取消分割多字节字符。仅和 -b 标志一起使用。如果字符的最后一个字节落在由 -b 标志的 List 参数指示的<br />范围之内,该字符将被写出;否则,该字符将被排除。

(2)cut一般以什么为依据呢? 也就是说,我怎么告诉cut我想定位到的剪切内容呢?

cut命令主要是接受三个定位方法:

第一,字节(bytes),用选项-b

第二,字符(characters),用选项-c

第三,域(fields),用选项-f

(3)以“字节”定位

举个例子吧,当你执行ps命令时,会输出类似如下的内容:

[[email protected] programming]$ who

rocrocket :0           2009-01-08 11:07

rocrocket pts/0        2009-01-08 11:23 (:0.0)

rocrocket pts/1        2009-01-08 14:15 (:0.0)

如果我们想提取每一行的第3个字节,就这样:

[[email protected] programming]$ who|cut -b 3

c

c

c

(4) 如果“字节”定位中,我想提取第3,第4、第5和第8个字节,怎么办?

-b支持形如3-5的写法,而且多个定位之间用逗号隔开就成了。看看例子吧:

[[email protected] programming]$ who|cut -b 3-5,8

croe

croe

croe

但有一点要注意,cut命令如果使用了-b选项,那么执行此命令时,cut会先把-b后面所有的定位进行从小到大排序,然后再提取。可不能颠倒定位的顺序哦。这个例子就可以说明这个问题:

[[email protected] programming]$ who|cut -b 8,3-5

croe

croe

croe

(5) 还有哪些类似“3-5”这样的小技巧,列举一下吧!

[[email protected] programming]$ who

rocrocket :0           2009-01-08 11:07

rocrocket pts/0        2009-01-08 11:23 (:0.0)

rocrocket pts/1        2009-01-08 14:15 (:0.0)

[[email protected] programming]$ who|cut -b -3

roc

roc

roc

[[email protected] programming]$ who|cut -b 3-

crocket :0           2009-01-08 11:07

crocket pts/0        2009-01-08 11:23 (:0.0)

crocket pts/1        2009-01-08 14:15 (:0.0)

想必你也看到了,-3表示从第一个字节到第三个字节,而3-表示从第三个字节到行尾。如果你细心,你可以看到这两种情况下,都包括了第三个字节“c”。

如果我执行who|cut -b -3,3-,你觉得会如何呢?答案是输出整行,不会出现连续两个重叠的c的。看:

[[email protected] programming]$ who|cut -b -3,3-

rocrocket :0           2009-01-08 11:07

rocrocket pts/0        2009-01-08 11:23 (:0.0)

rocrocket pts/1        2009-01-08 14:15 (:0.0)

(6)给个以字符为定位标志的最简单的例子吧!

下面例子你似曾相识,提取第3,第4,第5和第8个字符:

[[email protected] programming]$ who|cut -c 3-5,8

croe

croe

croe

不过,看着怎么和-b没有什么区别啊?莫非-b和-c作用一样? 其实不然,看似相同,只是因为这个例子举的不好,who输出的都是单字节字符,所以用-b和-c没有区别,如果你提取中文,区别就看出来了,来,看看中文提取的情况:

[[email protected] programming]$ cat cut_ch.txt

星期一

星期二

星期三

星期四

[[email protected] programming]$ cut -b 3 cut_ch.txt

?

?

?

?

[[email protected] programming]$ cut -c 3 cut_ch.txt

看到了吧,用-c则会以字符为单位,输出正常;而-b只会傻傻的以字节(8位二进制位)来计算,输出就是乱码。

既然提到了这个知识点,就再补充一句,如果你学有余力,就提高一下。

当遇到多字节字符时,可以使用-n选项,-n用于告诉cut不要将多字节字符拆开。

例子如下:

[[email protected] programming]$ cat cut_ch.txt |cut -b 2

?

?

?

?

[[email protected] programming]$ cat cut_ch.txt |cut -nb 2

[[email protected] programming]$ cat cut_ch.txt |cut -nb 1,2,3

(7)域是怎么回事呢?解释解释:


什么会有“域”的提取呢,因为刚才提到的-b和-c只能在固定格式的文档中提取信息,而对于非固定格式的信息则束手无策。这时候“域”就派上用场了。如果
你观察过/etc/passwd文件,你会发现,它并不像who的输出信息那样具有固定格式,而是比较零散的排放。但是,冒号在这个文件的每一行中都起到
了非常重要的作用,冒号用来隔开每一个项。

我们很幸运,cut命令提供了这样的提取方式,具体的说就是设置“间隔符”,再设置“提取第几个域”,就OK了!

以/etc/passwd的前五行内容为例:

[[email protected] programming]$ cat /etc/passwd|head -n 5

root:x:0:0:root:/root:/bin/bash

bin:x:1:1:bin:/bin:/sbin/nologin

daemon:x:2:2:daemon:/sbin:/sbin/nologin

adm:x:3:4:adm:/var/adm:/sbin/nologin

lp:x:4:7:lp:/var/spool/lpd:/sbin/nologin

[[email protected] programming]$ cat /etc/passwd|head -n 5|cut -d : -f 1

root

bin

daemon

adm

lp

看到了吧,用-d来设置间隔符为冒号,然后用-f来设置我要取的是第一个域,再按回车,所有的用户名就都列出来了!呵呵 有成就感吧!

当然,在设定-f时,也可以使用例如3-5或者4-类似的格式:

[[email protected] programming]$ cat /etc/passwd|head -n 5|cut -d : -f 1,3-5

root:0:0:root

bin:1:1:bin

daemon:2:2:daemon

adm:3:4:adm

lp:4:7:lp

[[email protected] programming]$ cat /etc/passwd|head -n 5|cut -d : -f 1,3-5,7

root:0:0:root:/bin/bash

bin:1:1:bin:/sbin/nologin

daemon:2:2:daemon:/sbin/nologin

adm:3:4:adm:/sbin/nologin

lp:4:7:lp:/sbin/nologin

[[email protected] programming]$ cat /etc/passwd|head -n 5|cut -d : -f -2

root:x

bin:x

daemon:x

adm:x

lp:x

(8)如果遇到空格和制表符时,怎么分辨呢?我觉得有点乱,怎么办?

有时候制表符确实很难辨认,有一个方法可以看出一段空格到底是由若干个空格组成的还是由一个制表符组成的。

[[email protected] programming]$ cat tab_space.txt

this is tab finish.

this is several space      finish.

[[email protected] programming]$ sed -n l tab_space.txt

this is tab\tfinish.$

this is several space      finish.$

看到了吧,如果是制表符(TAB),那么会显示为\t符号,如果是空格,就会原样显示。

通过此方法即可以判断制表符和空格了。

注意,上面sed -n后面的字符是L的小写字母哦,不要看错。

(9)我应该在cut -d中用什么符号来设定制表符或空格呢?

其实cut的-d选项的默认间隔符就是制表符,所以当你就是要使用制表符的时候,完全就可以省略-d选项,而直接用-f来取域就可以了。

如果你设定一个空格为间隔符,那么就这样:

[[email protected] programming]$ cat tab_space.txt |cut -d ‘ ‘ -f 1

this

this

注意,两个单引号之间可确实要有一个空格哦,不能偷懒。

而且,你只能在-d后面设置一个空格,可不许设置多个空格,因为cut只允许间隔符是一个字符。

[[email protected] programming]$ cat tab_space.txt |cut -d ‘ ‘ -f 1

cut: the delimiter must be a single character

Try `cut --help‘ for more information.

(10)cut有哪些缺陷和不足?

猜出来了吧?对,就是在处理多空格时。

如果文件里面的某些域是由若干个空格来间隔的,那么用cut就有点麻烦了,因为cut只擅长处理“以一个字符间隔”的文本内

时间: 2024-10-07 08:03:18

shell脚本的使用---cut截取数据的相关文章

shell脚本+mysql数据库组合进行数据安全监控

shell脚本 + mysql数据库 实现企业级会话边界控制器文件解析并告警 dirsx30001.sh处理文件,生成mysql备份文件的方式进行导入 #/bin/bash ##环境变量 path=/home/sbclog/sx30001 ##由于抓取的日志文件中没有年份参数,故导入系统年份参数,以达到数据库时间字段datetime ##也可以抓取tar包的名字中的字段 date_year=`date|cut -c 25-` #test ! -e $path/*.tar &&echo &q

《懒人Shell脚本》之七——格式化处理数据存入数据库实现

0.引言 实际应用开发中遇到:将非格式化的文件数据存储到数据库中.对于传统的格式化的数据:ini/json/xml我们都有现成的类库去实现.而对于如下非格式化的数据呢?以下是我的思考与实现. 数据截取片段如下所示: [[email protected] 2017]# head -n 10 input.txt [url]http://epaper.tianjinwe.com/mrxb/mrxb/2013-02/21/content_7566593.htm 新报讯[记者王晶通讯员赵子强]对31.66

shell脚本:字符串的截取

在shell脚本中我们所有变量的存储形式都是字符串.所以对于字符串的截取来说就变得十分重要了. 而在shell脚本中,如果想要对一个字符串进行指定的截取,有多种方法可以来完成:如下举例均用:STR="hello world my dear sister" ${STR#*char} 表示从左开始删除第一个char左边的所有字符,截取右边的字符串 #!/bin/bash STR="hello world my dear sister" echo ${STR} CUT=$

如何使用shell脚本快速排序和去重文件数据

前面写过一篇通过shell脚本去重10G数据的文章,见<用几条shell命令快速去重10G数据>.然而今天又碰到另外一个业务,业务复杂度比上次的单纯去重要复杂很多.找了很久没有找到相应的办法,于是用shell脚本程序去处理.具体业务逻辑: 1.首先根据给定指定进行排序 2.排序后对给定字段进行去重,去重的规则如下: a)排序后如果相邻N行给定字段值相同的行数不超过两行,则两行都保留. a)排序后如果相邻N行给定字段值相同的行数超过两行,则保留首行和尾行. 就这样一个业务逻辑,其实看起来并不是太

Saiku数据库迁移后的刷新脚本-Shell脚本读取数据库中的数据(二十三)

Saiku数据库迁移后的刷新脚本 之前有谈过对saiku中的数据进行刷新,因为saiku默认会从缓存中查询数据,但是配置不使用缓存又会效率低下... 所以这里就需要做一个数据刷新,每次ETL之后都需要执行一遍数据刷新脚本. 刷新脚本主要分为两部分 1.使用shell命令从数据库中读取已有的用户信息 (因为已经做过数据迁移,数据库已经从h2转为我们自己的mysql) saikuRefresh.sh #!/bin/bash #数据库连接信息 HOSTNAME="10.11.22.33" #

2018.4.21 五周第四次课(shell特殊符号,cut截取等命令)

shell特殊符号_cut命令 概念:cut命令用来截取某一个字段 格式:cut -d '分割字符' [-cf] n,这里的n是数字,该命令选项有如下几个: - d 后面跟分割字符,分割字符要用单引号括起来 - c 后面接的是第几个字符 - f 后面接的是第几个区块 cut命令用法如下 [[email protected] do]# cat /etc/passwd |head -2root:x:0:0:root:/root:/bin/bashbin:x:1:1:bin:/bin:/sbin/no

shell脚本变量和字符串截取

变量说明:$$ Shell本身的PID(ProcessID)$! Shell最后运行的后台Process的PID$? 最后运行的命令的结束代码(返回值)$- 使用Set命令设定的Flag一览$* 所有参数列表.如"$*"用「"」括起来的情况.以"$1 $2 - $n"的形式输出所有参数.[email protected] 所有参数列表.如"[email protected]"用「"」括起来的情况.以"$1″ &quo

Shell脚本8种字符串截取方法总结

Linux 的字符串截取很有用.有八种方法. 假设有变量 var=http://www.aaa.com/123.htm. 1. # 号截取,删除左边字符,保留右边字符. echo ${var#*//} 其中 var 是变量名,# 号是运算符,*// 表示从左边开始删除第一个 // 号及左边的所有字符即删除 http://结果是 :www.aaa.com/123.htm 2. ## 号截取,删除左边字符,保留右边字符. echo ${var##*/} ##*/ 表示从左边开始删除最后(最右边)一个

shell -脚本 给出多个数据列表 执行任务

方法1: #!/bin/bash USER=`cat iplist.txt` PASS=`cat passwd.txt` echo $USER SSH() { while true do     x=$1;shift;y=$2                //注意shift, 如果不进行移位操作,$1的值就不会变.                                  /usr/bin/expect <<-EOF spawn ssh [email protected]$x exp