当前位置:首页>python>对账从半天到5分钟,100行Python搞定

对账从半天到5分钟,100行Python搞定

  • 2026-09-06 05:41:55
对账从半天到5分钟,100行Python搞定

第1期我讲了"工作台壳子",一个HTML文件替代Notion。这期拆开第1期里埋的伏笔:凭证核对。


上回说到,我每天面对的活儿里有一项是「凭证核对:U8系统导出的数据要和Excel对,对完生成NCC导入格式」。

当时一笔带过了。

因为这事儿太具体,具体到我不想回忆。每个月末,从U8导出一沓凭证,再从网银下一沓流水,两边按金额、按摘要、按日期一条条肉眼勾。几百条,对完眼睛发直,还不敢说全对。

上回那个工作台,解决的是"今天干啥、干完没"的问题。这期解决的是"干的时候别要我命"的问题。


一、先说痛点,财务都懂

每月末的对账,本质就三件事:

  • 银行对账
    :U8账面流水 vs 银行对账单,找出未达账项
  • 往来对账
    :应收应付 vs 客户/供应商回单
  • 凭证勾对
    :同一笔业务,借方凭证和贷方凭证是不是配平

手工干是这样的:

步骤
手工做法
耗时
风险
导出
U8查凭证导出Excel,网银下载对账单
15分钟
格式每次都不一样
比对
按金额排序,肉眼一条条找对应
2-3小时
漏看、重看、看花
出差异
把对不上的抄到调节表
30分钟
抄错行
复核
再对一遍
1小时
人已经麻了

合计:半天起步,且出错率随条数指数上升。

我受够了的不是干活,是重复且低级的活。


二、我的方案:一段Python,不接任何外部系统

核心思路就一句:把"人眼匹配"换成"机器穷举匹配"。

数据不出本地,不传任何第三方对账平台,不买软件,一个 .py 文件双击就跑。

逻辑极简:

  1. 读U8导出的凭证表(pandas读Excel)
  2. 读银行流水/对方回单表
  3. 按「金额绝对值相等」做主键匹配,再用摘要关键词做二次校验
  4. 输出三张表:已对平、U8有对方无、对方有U8无

三、核心代码(极简版,约100行)

import pandas as pd

# 1. 读入两边的数据
u8 = pd.read_excel('u8_凭证.xlsx')        # 列:日期, 摘要, 借方, 贷方, 科目
bank = pd.read_excel('银行流水.xlsx')      # 列:日期, 摘要, 收入, 支出

# 2. 统一成"金额"一列(借贷/收支都转成带符号数)
u8['金额'] = u8['贷方'].fillna(0) - u8['借方'].fillna(0)
bank['金额'] = bank['收入'].fillna(0) - bank['支出'].fillna(0)

# 3. 按金额做主键匹配(金额相等即疑似一对)
merged = pd.merge(
    u8, bank,
    on='金额', how='outer',
    suffixes=('_u8', '_bank'),
    indicator=True
)

# 4. 拆出三种结果
matched   = merged[merged['_merge'] == 'both']          # 两边都有的 → 对平
only_u8   = merged[merged['_merge'] == 'left_only']     # 只有U8 → 未达/漏记
only_bank = merged[merged['_merge'] == 'right_only']    # 只有银行 → 未达/在途

# 5. 输出
with pd.ExcelWriter('对账结果.xlsx') as w:
    matched.to_excel(w, sheet_name='已对平', index=False)
    only_u8.to_excel(w, sheet_name='U8有-银行无', index=False)
    only_bank.to_excel(w, sheet_name='银行有-U8无', index=False)

print(f"对平 {len(matched)} 条,差异 {len(only_u8)+len(only_bank)} 条")

这就完了。

真实场景里你会加三样东西(都是十行内的事):

  • 日期窗
    :金额相等但差了半年的,大概率不是同一笔,加个 abs(日期差) < 5天 过滤
  • 摘要模糊匹配
    :用 摘要_u8.str.contains(关键词) 做二次确认,减少误配
  • 方向标记
    :金额相同但一借一贷的,标成"对冲"而非"未达"

但骨架就是上面这段。100行封顶。

文中这段是示意。文末同目录放了可直接运行的 auto_reconcile.py,已含日期窗过滤,拿来改改表头就能用。


四、为什么不用现成的?

方案
我的顾虑
网银自带对账
只能对自家账户,跨行/跨科目不灵活,规则写死
市面对账SaaS
要上传数据到第三方——财务数据脱敏前不敢传
找IT开发
排期两周起,改一次需求再排两周
自己写100行
数据不出本地,逻辑随改随用,今晚就能跑

我的原则没变:工具是为人服务的,不是人为工具服务的。

对账规则每个公司都不一样。买来的软件让你适应它的规则;自己写的,让规则适应你。


五、实际效果

跑了三个月,数字如下:

  • 对账耗时
    :从半天压缩到 5分钟(含导出)
  • 差异遗漏
    :从"凭眼力"到"机器穷举",0遗漏(前提是导出没漏行)
  • 顺带产出
    :自动生成了银行余额调节表模板,领导要的时候直接填
  • 最爽的一点
    :差异清单自动出来,我只需要去查那几十条"为什么对不上",而不是从头对一遍

省下的半天,我拿去做了行业消费分析。那才是财务该干的事,不是当人肉比对机。


六、给同行的提醒(重要)

  1. 先脱敏再跑
    :替换真实户名、账号、金额区间再丢给任何脚本/AI,别拿带全名的流水练手。
  2. 别删原始数据
    :脚本只做"读取+输出",永远不动源文件。对完发现漏了,重跑就行。
  3. 金额相同≠一定是一对
    :一定要加日期窗或摘要校验,否则会把两笔恰巧同额的错配在一起。
  4. 机器对平≠没问题
    :它只告诉你"两边都有这笔",不告诉你"这笔该不该发生"。最后的判断还是你的。

七、写在最后

第1期我说:最好的工具是让你少想多做的那个。

这期补一句:自动化替你干的,永远是那些不该占用你脑子的活。

把对账交给脚本,脑子留给分析。

下期我拆第1期里另一块——月结报表怎么从"每月手搓"变成"点一下出"。那是这个工作台真正值钱的内核。


技术栈:Python + pandas(读表/匹配),openpyxl(写Excel) 代码量:核心约100行,加校验不超过150行 配套脚本:同目录 auto_reconcile.py(含日期窗,可直接运行) 数据安全:全程本地运行,数据不出本机


本文记录我的对账自动化思路,不构成财务或技术建议。每个公司科目和导出格式不同,代码需按实际表结构调整。

最新文章

随机文章