一、批处理风格核心定义

批处理是经典数据处理架构风格,属于数据流架构分支,核心特征:

  1. 无实时交互:数据先批量采集、暂存,不边来边处理;
  2. 分阶段离线处理:固定输入→顺序多阶段转换→批量输出;
  3. 不依赖外部实时响应,运行时无用户 / 外部同步调用;
  4. 高吞吐、低实时性,适合海量数据统计、清算、对账、报表。

1. 核心四大特点(软考必背考点)

  1. 批量输入:数据源落地成文件 / 数据表,一次性加载,而非流式逐条消费;
  2. 阶段式转换:流水线分层处理,上一阶段输出作为下一阶段输入;
  3. 离线执行:定时调度(凌晨 / 非业务高峰),不占用在线交易资源;
  4. 批量输出:处理完成统一生成结果文件、报表、汇总库。

2. 优缺点(选择场景简答题考点)

优点
  • 架构简单、开发维护成本低;
  • 资源可控,错峰执行不影响在线业务;
  • 天然支持海量数据汇总、复杂计算;
  • 易重试、断点续跑、对账校验,金融场景强适配;
  • 数据一致性易保障,全量数据统一计算。
缺点
  • 延迟高,无法实时获取计算结果;
  • 数据异常只能整批重试,单条脏数据会阻塞整批;
  • 峰值资源占用大,调度窗口不足会积压;
  • 无法支撑实时查询、实时预警类需求。

3. 适用 / 不适用场景(选择题高频)

✅ 适合: 银行夜间清算、T+1 对账、日终报表、日志离线统计、批量代扣代发、大数据离线数仓、月度账单生成、税务批量申报。

❌ 不适合: 实时支付风控、实时用户推荐、实时监控告警、在线交互式查询。

二、批处理标准分层架构(软考标准模型)

标准三段式流水线,考试画图 / 论述题标准结构:

  1. 数据采集层(输入) 在线业务库、日志、上游文件落地到批量临时存储(文件 / ODS 数据表);
  2. 批处理计算层(核心流水线) 多阶段串行处理:清洗→转换→汇总→校验;
  3. 结果输出层 落地报表、结果库、对外传输文件、归档备份。

配套调度组件:定时任务框架(XXL-Job、Airflow、DataX、Hadoop YARN)、断点续跑、日志记录、异常告警。

三、与管道过滤器、流式处理的区分(易混淆考点)

  1. 批处理 vs 管道过滤器
    • 批处理:全量数据一次性加载,阶段执行完再进入下一阶段;
    • 管道过滤器:数据流逐条实时流转,不用等全部数据到位。
  2. 批处理 vs 实时流处理(Flink/Spark Streaming)
    • 批处理:有明确数据边界(昨日全量数据),T+1 延迟;
    • 流处理:无边界持续数据流,秒级 / 分钟级实时输出。

四、真实示例:银行信贷 T+1 批量代扣系统(金融场景,贴合软考真题业务)

业务背景

银行每日凌晨执行客户贷款批量代扣

  1. 前一日所有到期贷款客户信息存储在信贷业务库;
  2. 批量读取客户贷款、余额、还款计划;
  3. 校验账户状态、余额充足性;
  4. 扣划资金,生成扣款流水;
  5. 汇总对账文件,推送清算系统;
  6. 生成客户还款账单,归档备份。 完全离线批处理,白天不执行,属于典型批处理架构落地。

整体架构流程图

信贷在线业务库 → 【采集阶段】抽取当日到期贷款数据 → 临时批量数据表
        ↓
【清洗阶段】过滤销户、冻结、逾期黑名单客户
        ↓
【计算阶段】匹配还款计划,计算应扣本金+利息
        ↓
【扣划阶段】批量调用核心账务扣划接口,生成扣款流水
        ↓
【汇总校验阶段】统计成功笔数、失败笔数、总金额,对账平衡校验
        ↓
输出1:扣款流水表(存入数据仓库)
输出2:清算对账文件(推送总行清算系统)
输出3:客户日账单文件(归档存储7年)

分阶段详细代码 / 业务逻辑示例

阶段 1:数据批量采集(输入层)

使用 DataX 定时同步前一日到期贷款数据,一次性加载 10 万条批量数据,不逐条实时读取。

-- 批量抽取SQL,凌晨定时执行,一次性获取全量待处理数据
INSERT INTO batch_loan_temp (loan_id,cust_id,repay_amt,account_no,due_date)
SELECT id,customer_id,total_repay,bank_account,repay_date
FROM biz_loan
WHERE due_date = DATE_SUB(CURDATE(),INTERVAL 1 DAY) AND status = 'NORMAL';
阶段 2:数据清洗过滤(第一处理阶段)

批量过滤无效数据,删除黑名单、冻结账户,整批过滤后生成清洗中间表。

// Java批量处理,分页分批读取,统一过滤,无实时交互
public void batchCleanData() {
    int pageSize = 5000;
    long total = batchTempMapper.countAll();
    long pages = total / pageSize + 1;
    for (long i = 1; i <= pages; i++) {
        List<LoanTemp> batchList = batchTempMapper.selectPage(i, pageSize);
        List<LoanClean> cleanList = batchList.stream()
                .filter(item -> !blackListMapper.exists(item.getCustId())) // 过滤黑名单
                .filter(item -> accountMapper.getStatus(item.getAccountNo()).equals("NORMAL")) // 账户正常
                .map(this::convertToCleanData)
                .collect(Collectors.toList());
        cleanMapper.batchInsert(cleanList); // 批量插入清洗后数据
    }
}
阶段 3:业务计算与批量扣款(核心处理阶段)

批量计算本息,循环批次扣划,统一记录结果,不实时返回客户。

// 批量扣款核心逻辑,离线批处理,无前端实时等待
public void batchDeduct() {
    List<LoanClean> allCleanData = cleanMapper.selectAll();
    Map<String, List<LoanClean>> groupByAccount = allCleanData.stream()
            .collect(Collectors.groupingBy(LoanClean::getAccountNo));
    // 按账户批量扣划,一批次千条统一调用账务核心
    for (Map.Entry<String, List<LoanClean>> entry : groupByAccount.entrySet()) {
        String account = entry.getKey();
        List<LoanClean> deductList = entry.getValue();
        BigDecimal totalAmt = deductList.stream()
                .map(LoanClean::getRepayAmt)
                .reduce(BigDecimal.ZERO, BigDecimal::add);
        // 批量调用扣划,同步返回结果,批量写入流水
        DeductResp resp = coreAccountApi.batchDeduct(account, totalAmt);
        saveDeductRecord(deductList, resp);
    }
}
阶段 4:汇总对账校验(收尾阶段)

全量数据统计,校验借贷平衡,异常批量标记。

-- 批处理汇总统计SQL,生成对账结果
INSERT INTO batch_check_result (batch_date,total_count,success_count,fail_count,total_amt,success_amt)
SELECT 
    '2026-07-01',
    COUNT(*),
    SUM(CASE WHEN status='SUCCESS' THEN 1 ELSE 0 END),
    SUM(CASE WHEN status='FAIL' THEN 1 ELSE 0 END),
    SUM(repay_amt),
    SUM(CASE WHEN status='SUCCESS' THEN repay_amt ELSE 0 END)
FROM batch_deduct_record;

-- 对账校验:扣款总额 = 账务扣划总额,不平衡则标记批处理异常
SELECT a.success_amt, b.core_total_amt FROM batch_check_result a
LEFT JOIN core_batch_log b ON a.batch_date = b.batch_date
WHERE ABS(a.success_amt - b.core_total_amt) > 0;
阶段 5:批量输出文件(最终输出)

生成固定格式 txt 对账文件,批量上传文件服务器,归档存储。

# 输出对账文件示例内容(批量输出产物)
批次日期:20260630
总笔数:12689
成功笔数:12451
失败笔数:238
扣款总金额:15689234.62
明细:
LOAN001,CUST10001,652.30,SUCCESS
LOAN002,CUST10002,1250.00,FAIL,余额不足

配套调度与容错(软考论述加分点)

  1. 调度工具:XXL-Job 定时每日 02:00 触发批处理任务;
  2. 断点续跑:每阶段执行完成记录批次状态,失败后从当前阶段重跑,无需从头计算;
  3. 异常处理:整批失败发送邮件告警,失败数据单独落异常表,人工复核后重批;
  4. 资源隔离:批处理使用离线数据库,不占用在线交易库连接池,避免影响白天业务。

五、大数据场景批处理示例(Hadoop MapReduce,软考大数据考点)

场景:网站访问日志日离线统计

需求:每日凌晨统计昨日所有页面访问 UV、PV、访问时长,生成运营报表。

  1. 输入:昨日全量 Nginx 日志文件(批量落地 HDFS);
  2. Map 阶段:批量读取日志,提取用户 ID、页面 ID;
  3. Reduce 阶段:批量聚合每个页面访问次数、独立用户数;
  4. 输出:统计结果写入 Hive 数仓,供 BI 报表查询。

核心特征:全部数据先存储再一次性计算,无实时日志消费,标准批处理架构。

六、软考论述

1. 简述批处理架构风格

批处理架构属于数据流架构,将完整数据集作为输入,分多个离线阶段依次完成数据清洗、转换、聚合计算,全部处理完成后批量输出结果。采用定时调度离线执行,具备高吞吐、易对账、架构简单的优势,适合 T+1 统计、清算、批量数据加工;缺点是数据延迟高,无法满足实时业务需求。

2. 批处理架构设计要点

  1. 分层流水线设计:采集层、处理层、输出层解耦;
  2. 批量分块处理,避免一次性加载全量数据导致内存溢出;
  3. 增加批次状态记录,支持断点续跑;
  4. 独立离线资源池,隔离在线业务;
  5. 结果增加数据校验逻辑,保障批量数据一致性;
  6. 完善异常归档、告警、重跑机制。

更多推荐