排除 Python 中的隐藏文件

Exclude hidden files in Python

好吧,有一件事我必须做:我必须计算有或没有隐藏文件、有或没有递归、有或没有特定扩展名的文件(由用户决定)(CLI)。问题出在隐藏文件上。 我的方法:

if namespace.recursive == True:
    for files in os.walk(top=namespace.path, topdown=True): 
        for i in files[2]:
            countF += 1 
    print('Number of files in directory (with recursion): ', countF)
else: 
    p = Path(namespace.path)
    for subdirs in p.iterdir():
        if (subdirs.is_file()):
            count += 1
    print('Number of files in directory (without recursion): ', count)

计算隐藏文件的文件数。 我想做的事情:我希望这种方法可以计算没有隐藏文件的文件。但是如果用户输入 -h 参数,我只想计算隐藏文件。所以我试着为它做一个检查方法:

def check_attributes(filename):
    if(os.path.isfile(filename)):
        return win32api.GetFileAttributes(filename) & win32con.FILE_ATTRIBUTE_HIDDEN
    else:
        return 0

然后我尝试修改我的方法并在

之后添加
for i in files[2]:

类似于:

if check_attributes(f) == 0: #if it's not hidden - then count

但它仍然算作隐藏文件。我想了解如何做对。 非常感谢您的每一个回答! 编辑: 带检查的完整功能

def countFiles():
countF = int(0)
count = int(0)
c = int(0)
try:
    if namespace.extension == '.':
        if namespace.recursive == True:
            if namespace.hidden == False:
                for files in os.walk(top=namespace.path, topdown=True): 
                    for i in files[2]:
                        if check_attributes(i) == 0:
                            countF += 1 
                print('Number of files in directory (with recursion): ', countF)
        else: 
            if namespace.hidden == False:
                p = Path(namespace.path)
                for subdirs in p.iterdir():
                    if (subdirs.is_file()):
                        count += 1
                print('Number of files in directory (without recursion): ', count)
    else:
        if namespace.recursive == True:
            for files in os.walk(namespace.path):
                for f in files[2]:
                    if os.path.splitext(f)[1] == namespace.extension:
                        c += 1
            print('Number if files with extension ' + namespace.extension + ' in directory (without recursion):', c)
        else:
            for files in os.listdir(namespace.path):
                if os.path.splitext(files)[1] == namespace.extension:
                    c += 1
            print('Number if files with extension ' + namespace.extension + ' in directory (without recursion): ', c)
except Exception as e:
    print('Error:\n', e)
    sys.exit(0)

在您的原始代码中,有多个布尔参数创建了不同的路径。据我所知,您的 extension == '.' 路径是唯一调用 check_attributes 的路径,因此 可能 是问题所在。我决定尝试重写它。我重写它的方式有 2 个阶段:1. 递归或非递归地获取文件然后 2. 使用提供的 args 过滤文件。这是我想出的:

import argparse
import os
import win32api
import win32con


def count_files(args):
    files = []
    
    # Get the files differently based on whether recursive or not.
    if args.recursive:
        # Note here I changed how you're iterating. os.walk returns a list of tuples, so
        # you can unpack the tuple in your for. current_dir is the current dir it's in
        # while walking and found_files are all the files in that dir
        for current_dir, dirs, found_files in os.walk(top=args.path, topdown=True):
            files += [os.path.join(current_dir, found_file) for found_file in found_files]
    else
        # Note the os.path.join with the dir each file is in. It's important to store the
        # absolute path of each file.
        files += [os.path.join(args.path, found_file) for found_file in os.listdir(args.path)
                  if os.path.isfile(os.path.join(args.path, found_file))]
       
    filtered_files = []
    for found_file in files:
        print(found_file)
        if not args.hidden and (win32api.GetFileAttributes(found_file) & win32con.FILE_ATTRIBUTE_HIDDEN):
            continue  # hidden == False and file has hidden attribute, go to next one
        
        if args.extension and not found_file.endswith(args.extension):
            continue  # File doesn't end in provided extension
            
        filtered_files.append(found_file)
    
    print(f'Length: {len(filtered_files)}')
    return len(filtered_files)
    

if __name__ == '__main__':
    parser = argparse.ArgumentParser(description='Process some integers.')
    # Note that I took advantage of some other argparse features here like
    # required vs optional arguments and boolean types
    parser.add_argument('path')
    parser.add_argument('--recursive', action='store_true', default=False)
    parser.add_argument('--hidden', action='store_true', default=False)
    parser.add_argument('--extension', type=str)

    args = parser.parse_args()
    count_files(args)