当我通过ls滚动时,如果“filename”匹配,我怎么告诉grep只打印出行?我想让它忽略每一行上的所有内容,直到时间戳之后。必须有一些简单的方法才能在一个命令上执行此操作。
正如你所看到的,没有它,如果我搜索文件“rwx”,它不仅会返回rwx.c行,还会返回前三行因为权限。我打算使用AWK,但如果我搜索“rwx”,我希望它显示整个最后一行。
有什么想法吗?
编辑:感谢下面的黑客攻击。但是,拥有更多无错误的方法会很棒。例如,如果我有一个名为“rob rob”的文件,我将无法使用所述解决方案。drwxrwxr-x 2 rob rob 4096 2012-03-04 18:03 .
drwxrwxr-x 4 rob rob 4096 2012-03-04 12:38 ..
-rwxrwxr-x 1 rob rob 13783 2012-03-04 18:03 a.out
-rw-rw-r-- 1 rob rob 4294 2012-03-04 18:02 function1.c
-rw-rw-r-- 1 rob rob 273 2012-03-04 12:54 function1.c~
-rw-rw-r-- 1 rob rob 16 2012-03-04 18:02 rwx.c
-rw-rw-r-- 1 rob rob 16 2012-03-04 18:02 rob rob
答案 0 :(得分:12)
以下内容仅列出文件名,每行列出一个文件。
$ ls -1
包含。文件
$ ls -1a
请注意,参数为数字“1”,而不是字母“l”。
答案 1 :(得分:3)
为什么不使用grep并匹配时间戳后面的文件名?
grep -P "[0-9]{2}:[0-9]{2} $FILENAME(\.[a-zA-Z0-9]+)?$"
[0-9]{2}:[0-9]{2}
是暂时的,$FILENAME
是您放置rob rob
或rwx
的位置,尾随(\.[a-zA-Z0-9]+)?
是允许的可选的扩展名。
编辑:@JonathanLeffler下面指出,当文件超过6个月时,时间列被一年替换 - 这就是我的电脑无论如何都会发生的事情。您可以([0-9]{2}:[0-9]{2}|(19|20)[0-9]{2})
允许时间或年,但您可能最好使用awk(?)。
[foo@bar ~/tmp]$ls -al
total 8
drwxrwxr-x 2 foo foo 4096 Mar 5 09:30 .
drwxr-xr-- 83 foo foo 4096 Mar 5 09:30 ..
-rw-rw-r-- 1 foo foo 0 Mar 5 09:30 foo foo
-rw-rw-r-- 1 foo foo 0 Mar 5 09:29 rwx.c
-rw-rw-r-- 1 foo foo 0 Mar 5 09:29 tmp
[foo@bar ~/tmp]$export filename='foo foo'
[foo@bar ~/tmp]$echo $filename
foo foo
[foo@bar ~/tmp]$ls -al | grep -P "[0-9]{2}:[0-9]{2} $filename(\.[a-zA-Z0-9]+)?$"
-rw-rw-r-- 1 cha66i cha66i 0 Mar 5 09:30 foo foo
(如果你愿意,你可以另外扩展到匹配整行:
^ # start of line
[d-]([r-][w-][x-]){3} + # permissions & space (note: is there a 't' or 's'
# sometimes where the 'd' can be??)
[0-9]+ # whatever that number is
[\w-]+ [\w-]+ + # user/group (are spaces allowed in these?)
[0-9]+ + # file size (modify for -h switch??)
(19|20)[0-9]{2}- # yyyy (modify if you want to allow <1900)
(1[012]|0[1-9])- # mm
(0[1-9]|[12][0-9]|3[012]) + # dd
([01][0-9]|2[0-3]):[0-6][0-9] +# HH:MM (24hr)
$filename(\.[a-zA-Z0-9]+)? # filename & optional extension
$ # end of line
。你明白了这一点,根据你的需要量身定做。)
答案 2 :(得分:2)
假设你不准备这样做:
ls -ld $(ls -a | grep rwx)
然后你需要利用在文件名开始之前有8个空格分隔列的事实。使用egrep
(或grep -E
),您可以执行以下操作:
ls -al | egrep "^([^ ]+ +){8}.*rwx"
这在第8列之后查找'rwx'。如果您希望名称以rwx
开头,请忽略.*
。如果您希望名称以rwx
结尾,请在结尾添加$。请注意,我使用了双引号,因此您可以插入变量来代替文字rwx
。
这是在Mac OS X 10.7.3上测试的; ls -l
命令始终为日期字段提供三列:
-r--r--r-- 1 jleffler staff 6510 Mar 17 2003 README,v
-r--r--r-- 1 jleffler staff 26676 Mar 3 21:44 ccs.nmd
您的ls -l
似乎只提供了两列,因此您需要将机器的{8}
更改为{7}
,并注意在系统之间进行迁移。
答案 3 :(得分:1)
好吧,如果你正在使用没有空格的文件名,你可以这样做:
grep 'rwx\S*$'
答案 4 :(得分:0)
作为一个简单的hack,只需在文件名之前添加一个空格,这样就不会与输出的开头匹配:
ls -al | grep '\srwx'
编辑:好的,这不像应该的那样健壮。这是awk:
ls -l | awk ' $9 ~ /rwx/ { print $0 }'
答案 5 :(得分:0)
除了你可以使用模式匹配ls,exaple ksh和bash之外, 这可能是你应该做的,你可以使用文件名出现在a中的事实 固定位置。 awk(gawk,nawk或者你有)是一个更好的选择。 如果你必须使用grep它闻起来像家庭作业给我。请用这种方式标记。
假设文件名起始位置基于linux中ls -l的输出:56
-rwxr-xr-x 1 Administrators None 2052 Feb 28 20:29 vote2012.txt
ls -l | awk ' substr($0,56) ~/your pattern even with spaces goes here/'
如,
ls -l | awk ' substr($0,56) ~/^val/'
将找到以“val”
开头的文件答案 6 :(得分:0)
这对我有用,不像ls -l&amp;一些人指出的其他人。我喜欢这个,因为它非常通用&amp;给我基本文件名,它删除文件前的路径名。
ls -1 /path_name |awk -F/ '{print $NF}'
答案 7 :(得分:0)
您只需要一个命令 -
ls -al | gawk '{print $9}'
答案 8 :(得分:0)
您可以使用:
ls -p | grep -v /
答案 9 :(得分:0)
这是超老的,但我需要答案,很难找到它。我不是很在乎单线部分。我只需要完成它。这是肮脏的,需要您对列进行计数。我不是在这里寻找支持,只是为将来的搜索者留下了一些选择。
有用的awk
技巧是here- 使用awk打印从第n个到最后一个的所有列
如果
YOUR_FILENAME="rob rob"
和
WHERE_FILENAMES_START=8
ls -al | while read x; do
y=$(echo "$x" | awk '{for(i=$WHERE_FILENAMES_START; i<=NF; ++i) printf $i""FS; print ""}')
[[ "$YOUR_FILENAME " = "$y" ]] && echo "$x"
done
如果将其另存为bash脚本,并用$ 2和$ 1替换var,将脚本放入usr bin中,那么您将获得干净的单线;)
输出将是:
> -rw-rw-r-- 1 rob rob 16 2012-03-04 18:02 rob rob
问题是单线的,所以...
ls -al | while read x; do [[ "$YOUR_FILENAME " = "$(echo "$x" | awk '{for(i=WHERE_FILENAMES_START; i<=NF; ++i) printf $i""FS; print ""}')" ]] && echo "$x" ; done
(大声笑; P)
在另一个注释上:radical.coffee your answer。它没有解决我这个问题的版本,所以我没有赞成,但我喜欢您的正则表达式细目:D