NiceBlueChai/cc_loc_tool

一个使用 Rust 语言开发的 C/C++ 代码行统计工具,提供友好的 GUI 界面,支持快速扫描、统计和分析 C/C++ 项目的代码行、注释行和空白行。

★ 0Forks 0RustGitHub ↗Compare

README

C/C++ 代码行统计工具 (cc_loc_tool)

一个使用 Rust 语言开发的 C/C++ 代码行统计工具,提供友好的 GUI 界面,支持快速扫描、统计和分析 C/C++ 项目的代码行、注释行和空白行。

功能特性

  • 📁 目录扫描:支持扫描指定目录下的所有支持的源代码文件
  • 📊 详细统计:分别统计代码行、注释行、空白行的数量
  • 🧮 复杂度分析:统计圈复杂度、函数总数、高复杂度函数与最长函数
  • 🔍 复杂度详情:鼠标移到结果行上点「详情」,查看该文件每个函数的复杂度
  • 👀 文件预览:在应用内直接查看源码,不必切到编辑器
  • ⚙️ 灵活过滤:支持排除指定目录和文件(支持通配符 *)
  • 📈 结果排序:可按文件路径、代码行、注释行等多维度排序
  • 🎨 友好界面:使用现代化 GUI 框架,直观展示统计结果
  • 🌐 编码支持:自动识别 UTF-8 和 GBK 编码的文件
  • 🌍 多语言支持:支持 C, C++, Java, Python, Go, Rust 等多种编程语言
  • 🧩 文件类型自定义:支持按扩展名自定义额外扫描文件类型
  • 💾 配置保存:设置改动即时落盘,下次启动自动恢复
  • 📸 历史对比:保存扫描快照并与历史结果对比差异
  • 📤 导出功能:支持导出统计结果到 CSV, JSON, HTML 格式
  • 🖥️ 命令行界面:提供 CLI 版本,支持批量处理和自动化
  • ⚡ 并行扫描:使用多线程并行处理,提高大项目扫描速度
  • 🗂️ 扫描缓存:目录内容未变化时复用缓存结果,避免重复扫描
  • 📊 进度显示:扫描过程中实时显示进度条和处理文件数
  • 🌓 深色主题:支持浅色/深色主题切换,保护眼睛
  • ⌨️ 快捷键与菜单:常用操作都可以用快捷键或菜单触发
  • 📱 响应式布局:优化不同屏幕尺寸下的界面显示

界面截图

程序主界面

界面展示了项目的主要功能:

  • 左侧设置区:项目目录、排除规则、自定义后缀、统计语言、复杂度开关
  • 顶部操作:导出结果、保存快照、历史对比、重新扫描
  • 统计概览:文件数、代码行、注释行、空白行、总计
  • 复杂度概览:平均复杂度、函数总数、高复杂度函数、最长函数
  • 结果表:按列排序,鼠标移到行上出现「详情」按钮,可直接打开复杂度详情窗口
  • 深色/浅色主题切换功能

支持的文件类型

C/C++

  • 源代码文件:.c, .cc, .cpp, .cxx
  • 头文件:.h, .hpp, .hxx
  • 内联文件:.inl

Java

  • 源代码文件:.java

Python

  • 源代码文件:.py

Go

  • 源代码文件:.go

Rust

  • 源代码文件:.rs

技术栈

  • 语言:Rust 2024
  • GUI 框架:gpui-kit(内含 GPUI 与 GPUI Component 组件库)
  • 依赖管理:Cargo
  • 文件系统:walkdir
  • 错误处理:anyhow
  • 编码处理:encoding_rs
  • 配置管理:toml
  • 并发处理:rayon
  • 数据序列化:serde_json
  • CSV 导出:csv
  • HTML 处理:html-escape
  • 日期处理:chrono
  • 系统目录:dirs

安装与运行

环境要求

  • Rust 1.85+(edition 2024,推荐使用最新稳定版)

编译与运行

# 克隆项目
git clone <项目地址>
cd cc_loc_tool

# 编译并运行 GUI
cargo run --bin cc_loc_tool

# 编译并运行命令行版
cargo run --bin cc_loc_cli -- ./my_project

本包有两个可执行目标,cargo run 不带 --bin 会报「could not determine which binary to run」。

使用说明

GUI 界面

  1. 选择目录:点击「浏览...」按钮选择要扫描的项目目录
  2. 选择语言:勾选要统计的编程语言(支持多语言同时统计)
  3. 配置过滤:
    • 在「排除目录」输入框中填写要排除的目录名,用逗号或分号分隔
    • 在「排除文件」输入框中填写要排除的文件名(支持通配符 *)
  4. 开始扫描:点击「开始扫描」按钮开始统计,实时显示进度;扫描中可用 Esc 取消
  5. 查看结果:扫描完成后查看统计摘要、复杂度概览和详细文件列表
  6. 排序结果:点击表格表头可按对应列排序
  7. 查看细节:鼠标移到结果行上点「详情」查看该文件的函数级复杂度,点「打开文件」预览源码
  8. 导出结果:点击「导出结果」按钮选择导出格式和路径
  9. 历史对比:先「保存快照」,之后「历史对比」查看与快照的差异

快捷键

快捷键 功能
Ctrl/Cmd + O 选择项目目录
Ctrl/Cmd + R 开始扫描
Esc 取消扫描
Ctrl/Cmd + E 导出结果
Ctrl/Cmd + S 保存快照
Ctrl/Cmd + Shift + S 历史对比
Ctrl/Cmd + D 切换主题
Enter 打开选中文件
Ctrl/Cmd + I 查看选中文件的复杂度详情
Ctrl/Cmd + C 复制选中文件路径

命令行界面 (CLI)

# 编译 CLI 版本
cargo build --bin cc_loc_cli

# 基本用法
cc_loc_cli <目录路径>

# 示例
cc_loc_cli ./my_project

# 排除指定目录和文件
cc_loc_cli -d ./my_project -e build,target -f moc_*,*.generated.cpp

# 仅统计特定语言
cc_loc_cli -d ./my_project -l C++,Java,Python

# 自定义额外文件扩展名
cc_loc_cli -d ./my_project -x tpp,ipp,cu

# 导出结果到文件
cc_loc_cli -d ./my_project -o results.csv -t csv

# 附带复杂度分析
cc_loc_cli -d ./my_project -c

# 保存快照 / 与历史快照对比
cc_loc_cli -d ./my_project --save-snapshot snap_v1.json
cc_loc_cli -d ./my_project --compare-with snap_v1.json

# 查看帮助信息
cc_loc_cli --help

命令行选项:

  • -d, --directory:要扫描的目录路径(也可直接作为位置参数给出)
  • -e, --exclude-dirs:要排除的目录列表,用逗号或分号分隔
  • -f, --exclude-files:要排除的文件模式,用逗号或分号分隔
  • -l, --languages:要扫描的编程语言,用逗号或分号分隔(支持:C, C++, Java, Python, Go, Rust)
  • -x, --extensions:自定义扫描后缀,用逗号或分号分隔(可带或不带 .,如 tpp,ipp,cu)
  • -c, --complexity:启用代码复杂度分析
  • --save-snapshot PATH:把本次扫描结果存成 JSON 快照
  • --compare-with PATH:与指定快照对比,输出差异摘要
  • -o, --output:导出结果的文件路径
  • -t, --format:导出格式(csv, json, html)
  • -h, --help:显示帮助信息
  • -v, --version:显示版本信息

默认排除项

以下是新配置(首次运行、或配置文件里没有这两项时)的默认值,可以在界面上直接改,改动即时写回配置文件。

目录

  • node_modules
  • .git
  • target

文件

  • *.generated.*
  • moc_*
  • qrc_*

另外无需配置就会排除的:名字以 . 开头的条目一律跳过,目录和文件都跳(所以 .gitignore、.clang-format 这类文件不会被统计)。扫描根目录本身不受这条限制,-d .、-d .. 或直接指定点开头的目录都能正常扫描。

匹配规则有个不对称要注意:排除目录是按目录名精确匹配(区分大小写,只匹配名字不含路径);排除文件是按文件名做通配符匹配(*,大小写不敏感,同样不含路径)。

项目结构

cc_loc_tool/
├── src/
│   ├── main.rs              # GUI 程序入口
│   ├── cli_main.rs          # CLI 程序入口
│   ├── lib.rs               # 库入口(GUI 与 CLI 共用)
│   ├── cli.rs               # 命令行界面实现
│   ├── config.rs            # 配置文件处理
│   ├── export.rs            # 导出功能实现(CSV/JSON/HTML)
│   ├── history.rs           # 快照保存与历史对比
│   ├── language.rs          # 语言与扩展名定义
│   ├── loc/                 # 代码统计核心模块
│   │   ├── counter.rs       # 文件行统计逻辑
│   │   ├── scanner.rs       # 目录扫描逻辑
│   │   └── mod.rs           # 模块导出
│   ├── complexity/          # 复杂度分析
│   │   ├── cyclomatic.rs    # 圈复杂度计算
│   │   ├── function_stats.rs# 函数提取与统计
│   │   ├── metrics.rs       # 文件级指标聚合
│   │   └── mod.rs           # 模块导出
│   └── ui/                  # UI 界面模块
│       ├── mod.rs           # 主题、滚动条、初始化
│       ├── view.rs          # 主视图与页面切换
│       ├── results.rs       # 结果表(列、排序、行操作)
│       ├── detail.rs        # 复杂度详情窗口
│       ├── preview.rs       # 文件预览窗口
│       ├── actions.rs       # 动作、快捷键与应用菜单
│       ├── state.rs         # 界面状态与主题
│       └── windows.rs       # 多窗口管理
├── assets/screenshot.png    # 界面截图
├── .github/workflows/ci.yml # fmt / test / clippy 三条门禁
├── AGENTS.md                # 贡献者与 AI 代理的仓库约束
├── Cargo.toml               # 项目配置和依赖
└── Cargo.lock               # 依赖版本锁定

核心功能实现

代码行统计算法

  1. 文件编码检测:先按 UTF-8 流式逐行读;解码报错才回退,把整个文件读出来按 UTF-8 宽松解码、仍失败则按 GBK 解码
  2. 行类型识别(按语言分支):
    • 空白行:trim() 后为空的行
    • C 系(C/C++/Java/Go/Rust):// 开头算注释,/* 开头或行内含 /* 进入块注释
    • Python:# 开头算注释,""" / ''' 包裹的行按多行注释处理
    • 代码行:以上都不是
  3. 块注释处理:跨多行的 /* */、以及 Python 的三引号块都能正确连续计数

目录扫描算法

  1. 递归遍历:使用 walkdir 库递归遍历目录
  2. 文件过滤:
    • 按已选语言的扩展名匹配(外加自定义后缀),大小写不敏感
    • 跳过名字以 . 开头的条目(目录和文件都跳)
    • 应用用户指定的排除目录 / 排除文件规则
  3. 并发优化:rayon 并行统计单文件,GUI 侧在后台线程扫描,不阻塞界面

性能特点

  • 并行扫描:文件级 rayon 并行,配合进程内结果缓存(同一目录配置未变时复用,最多 8 条)
  • 内存友好:普通统计走 BufReader 逐行流式,不把整文件读进内存;只有非 UTF-8 文件和开复杂度分析时才整体读入
  • 大文件保护:开启复杂度分析时,超过 1 MiB 的文件退回逐行统计并跳过复杂度(避免为算复杂度而吃下大文件)
  • UI 响应:扫描过程中界面保持响应,可随时取消

下一步计划

功能增强

  • 支持更多编程语言(Java、Python、Go、Rust 等)
  • 配置文件支持(自动保存和加载用户设置)
  • 增加导出功能(CSV、JSON、HTML)
  • 增加代码复杂度分析(复杂度详情窗口)
  • 支持命令行界面 (CLI)
  • 支持历史快照与对比
  • 提供项目分析报告生成

性能优化

  • 实现并行扫描,提高大项目处理速度
  • 优化内存使用,支持处理超大型项目
  • 增加缓存机制,避免重复扫描

UI 改进

  • 增加进度条显示扫描进度
  • 支持深色/浅色主题切换
  • 提供文件预览功能
  • 增加统计图表可视化
  • 结果表滚动条不再遮挡内容

贡献

欢迎提交 Issue 和 Pull Request 来帮助改进这个项目!

许可证

MIT License

Contributors

NiceBlueChai

Issues