微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

使用Python的os.walk函数和ls命令获得了不同的结果

#!/bin/python
import os
pipe=os.popen("ls /etc -alR| grep \"^[-l]\"|wc -l")         #Expr1
a=int(pipe.read())
pipe.close()
b=sum([len(files) for root,dirs,files in os.walk("/etc")])  #Expr2
print a
print b
print "a equals to b ?", str(a==b)  #False
print "Why?"

Expr1的功能和Expr2的区别是什么?
我认为Expr1给出了正确答案,但不确定.

解决方法:

简短回答:

ls -laR | grep“^ [ – l]”将符号链接计入目录.
它匹配以l开头并包含符号链接到目录的任何行.

相比之下,[os.walk(‘/ etc’)中root,dirs,files的文件]
不计算符号链接到目录.它忽略所有目录并仅列出文件.

答案很长:

以下是我发现差异的方法

import os
import subprocess
import itertools

def line_to_filename(line):
    # This assumes that filenames have no spaces, which is a false assumption
    # Ex: /etc/NetworkManager/system-connections/Wired connection 1
    idx = line.rfind('->')
    if idx > -1:
        return line[:idx].split()[-1]
    else:
        return line.split()[-1]

line_to_filename尝试在ls -laR的输出查找文件名.

这定义了expr1和expr2,它与您的代码基本相同.

proc=subprocess.Popen(
    "ls /etc -alR 2>/dev/null | grep -s \"^[-l]\" ", shell = True,
    stdout = subprocess.PIPE)         #Expr1
out, err = proc.communicate()
expr1 = map(line_to_filename, out.splitlines())

expr2 = list(itertools.chain.from_iterable(
    files for root,dirs,files in os.walk('/etc') if files))  #Expr2

for expr in ('expr1', 'expr2'):
    print '{e} is of length {l}'.format(e = expr, l = len(vars()[expr]))

这将删除expr1中同样位于expr2中的名称

for name in expr2:
    try:
        expr1.remove(name)
    except ValueError:
        print('{n} is not in expr1'.format(n = name))

删除expr1和expr2共享的文件名后,

print(expr1) 

产量

['i386-linux-gnu_xorg_extra_modules', 'nvctrl_include', 'template-dkms-mkdsc', 'run', '1', 'conf.d', 'conf.d']

然后我用find在/ etc中找到这些文件并试图猜出这些文件的异常.它们是目录(而不是文件)的符号链接.

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐