删除列

sh/bash/dash/ksh/zsh等Shell脚本
回复
mad_frog
帖子: 55
注册时间: 2011-06-29 11:26

删除列

#1

帖子 mad_frog » 2011-10-26 9:58

求方法实现删除列操作
1 2 3 5 1
2 0 a 3 4 5
1 0 2 3 a 4
1 2 4 5 4
1 3 2 a 4
如果第二列出现了“0”,则删除该列,效果如下:
1 2 3 5 1
2 a 3 4 5
1 2 3 a 4
1 2 4 5 4
1 3 2 a 4
头像
Methuselar
帖子: 122
注册时间: 2009-06-04 12:06
联系:

Re: 删除列

#2

帖子 Methuselar » 2011-10-27 15:34

我有个很脏的做法不知道是否不妥...

代码: 全选

awk '$2 == "0" {$2="\b"} {print}'
Mea Culpa!
头像
lilydjwg
论坛版主
帖子: 4258
注册时间: 2009-04-11 23:46
系统: Arch Linux
联系:

Re: 删除列

#3

帖子 lilydjwg » 2011-10-27 16:35

Methuselar 写了:我有个很脏的做法不知道是否不妥...

代码: 全选

awk '$2 == "0" {$2="\b"} {print}'
很显然不妥,你把结果拿到文本编辑器里看看?看不清楚就用十六进制编辑器。
头像
eexpress
帖子: 58428
注册时间: 2005-08-14 21:55
来自: 长沙

Re: 删除列

#4

帖子 eexpress » 2011-10-27 16:39

● cat t |sed '/.*\ 0\>/d'
# ● 2011-10-27_16:43:40
1 2 3 5 1
1 2 4 5 4
1 3 2 a 4
● 鸣学
头像
Methuselar
帖子: 122
注册时间: 2009-06-04 12:06
联系:

Re: 删除列

#5

帖子 Methuselar » 2011-10-27 16:41

lilydjwg 写了:
Methuselar 写了:我有个很脏的做法不知道是否不妥...

代码: 全选

awk '$2 == "0" {$2="\b"} {print}'
很显然不妥,你把结果拿到文本编辑器里看看?看不清楚就用十六进制编辑器。
:P 老老实实正则或是循环吧...如果赋值开销不太大...

代码: 全选

awk '$2 == "0" {for(i=2; i<=NF; i++){ $i=$((i+1))};NF=NF-1 } {print}'
PS: EE 你把人家一行都删了....
Mea Culpa!
fnan
帖子: 919
注册时间: 2009-07-01 22:04

Re: 删除列

#6

帖子 fnan » 2011-10-27 21:05

kose3@kose3-laptop:~$ cat 1.t
1 2 3 5 1
2 0 a 3 4 5
1 0 2 3 a 4
1 2 4 5 4
1 3 2 a 4
1 2 0 30 5
1 10 30 5
kose3@kose3-laptop:~$ sed -r 's/^(\S+)\s\S*0\S*/\1/' 1.t
1 2 3 5 1
2 a 3 4 5
1 2 3 a 4
1 2 4 5 4
1 3 2 a 4
1 2 0 30 5
1 30 5
bash不如perl精妙,学不到lisp的皮毛,远不够c++强悍,不过可以用。
头像
Methuselar
帖子: 122
注册时间: 2009-06-04 12:06
联系:

Re: 删除列

#7

帖子 Methuselar » 2011-10-28 0:32

这样老老实实的C写法可能性能会高点...

代码: 全选

awk '$2 == "0" {printf $1; for (i=3; i<=NF; i++) {printf(" %s", $i)}; print "";next}1'
突然想起来awk的sub...针对第2列的话语句会很短

代码: 全选

awk '$2 == "0" {sub($1" 0", $1, $0)}1'
都是hardcode...要是awk有cut -f3-这样好用的操作符就好了...

代码: 全选

awk '$2 == "0" {printf("%s%s", $1,FS); system("echo "$0" | cut -d\""FS"\"  -f3-"); next;}1'
Mea Culpa!
fnan
帖子: 919
注册时间: 2009-07-01 22:04

Re: 删除列

#8

帖子 fnan » 2011-10-28 5:49

awk '$2~/0/ {sub(" "$2,"")}1'
bash不如perl精妙,学不到lisp的皮毛,远不够c++强悍,不过可以用。
MaskRay
帖子: 61
注册时间: 2010-04-29 22:00
系统: Gentoo Linux ~amd64
联系:

Re: 删除列

#9

帖子 MaskRay » 2011-11-06 17:01

代码: 全选

colrm 2 3
bellszhu
帖子: 108
注册时间: 2010-12-18 19:46

Re: 删除列

#10

帖子 bellszhu » 2011-11-21 11:01

Methuselar 写了:这样老老实实的C写法可能性能会高点...

代码: 全选

awk '$2 == "0" {printf $1; for (i=3; i<=NF; i++) {printf(" %s", $i)}; print "";next}1'
突然想起来awk的sub...针对第2列的话语句会很短

代码: 全选

awk '$2 == "0" {sub($1" 0", $1, $0)}1'
都是hardcode...要是awk有cut -f3-这样好用的操作符就好了...

代码: 全选

awk '$2 == "0" {printf("%s%s", $1,FS); system("echo "$0" | cut -d\""FS"\"  -f3-"); next;}1'
awk '$2 == "0" {printf $1; for (i=3; i<=NF; i++) {printf(" %s", $i)}; print "";next}1'
中的,最后面的1 表示什么意思??
keep the faith
头像
Ubuntu与Linux
帖子: 1211
注册时间: 2010-06-09 19:57

Re: 删除列

#11

帖子 Ubuntu与Linux » 2011-11-21 13:40

这不是删除列吧,是删除那个位置的‘0’?
头像
Methuselar
帖子: 122
注册时间: 2009-06-04 12:06
联系:

Re: 删除列

#12

帖子 Methuselar » 2011-11-21 14:51

大括号以外的awk表达式,awk检查其是否为数字0, 大于0时awk输出,0时或非数字不输出. 基本就是如此, 所以“1”用来简洁的让awk程序输出当前行
Mea Culpa!
bellszhu
帖子: 108
注册时间: 2010-12-18 19:46

Re: 删除列

#13

帖子 bellszhu » 2011-11-21 16:05

Methuselar 写了:大括号以外的awk表达式,awk检查其是否为数字0, 大于0时awk输出,0时或非数字不输出. 基本就是如此, 所以“1”用来简洁的让awk程序输出当前行
哦,原来这样。谢谢了
keep the faith
回复