import os import sys def get_size_format(b, factor=1024, suffix="B"): """ 将字节大小转换为更易读的格式 (KB, MB, GB, 等) """ for unit in ["", "K", "M", "G", "T", "P", "E", "Z"]: if b < factor: return f"{b:.2f} {unit}{suffix}" b /= factor return f"{b:.2f} Y{suffix}" def get_directory_size(directory): """ 递归获取文件夹总大小(字节) 使用 os.scandir 比 os.walk 更快 """ total = 0 try: for entry in os.scandir(directory): if entry.is_file(follow_symlinks=False): total += entry.stat(follow_symlinks=False).st_size elif entry.is_dir(follow_symlinks=False): total += get_directory_size(entry.path) except PermissionError: # 跳过无权限访问的文件夹/文件 pass except FileNotFoundError: pass except Exception: pass return total def scan_folders(target_dir): """ 扫描目标目录下的子文件夹和文件,并按大小降序输出 """ print(f"开始扫描目录: {target_dir}\n") if not os.path.exists(target_dir): print(f"路径不存在: {target_dir}") return items_sizes = [] try: for entry in os.scandir(target_dir): if entry.is_dir(follow_symlinks=False): size = get_directory_size(entry.path) items_sizes.append({'name': entry.name, 'size': size, 'path': entry.path, 'type': '文件夹'}) elif entry.is_file(follow_symlinks=False): size = entry.stat(follow_symlinks=False).st_size items_sizes.append({'name': entry.name, 'size': size, 'path': entry.path, 'type': '文件'}) except PermissionError: print(f"警告: 没有权限访问目录 '{target_dir}'。") return # 按大小降序排序 items_sizes.sort(key=lambda x: x['size'], reverse=True) # 打印结果表头 # 由于中文宽度问题,简单格式化可能无法完美对齐,这里尽量保证可读性 print(f"{'类型':<5} | {'大小':<12} | {'名称'}") print("-" * 60) total_size = 0 for item in items_sizes: size_str = get_size_format(item['size']) print(f"{item['type']:<5} | {size_str:<12} | {item['name']}") total_size += item['size'] print("-" * 60) print(f"当前目录总大小: {get_size_format(total_size)}") if __name__ == "__main__": # 如果通过命令行传入参数,则使用参数作为路径,否则提示用户输入或默认扫描当前目录 if len(sys.argv) > 1: target = sys.argv[1] else: target = input("请输入要扫描的文件夹路径 (按回车扫描当前目录): ").strip() if not target: target = "." # 获取绝对路径并执行扫描 target_abs = os.path.abspath(target) scan_folders(target_abs)