You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

SQL Server中利用函数生成半月度摊销计划到期日

解决半月度摊销计划的到期日填充问题

你的duedategenerator函数逻辑完全没问题,能够正确处理半月度的到期日规则(每月15日/月末,二月特殊处理月末)。不过你之前尝试的LAG窗口函数方式无法实现递推生成——因为LAG只能取结果集中已有的上一行数据,而后续NULL行的到期日需要依赖前一期已生成的正确日期,这里用递归CTE是更合适的方案。

步骤1:确保你的函数已正确创建

如果还没创建duedategenerator函数,先执行这段代码:

CREATE FUNCTION dbo.duedategenerator(@dt DATE)
RETURNS DATE
AS
BEGIN
    RETURN CASE 
        WHEN DAY(@dt) < 16 THEN 
            CASE WHEN MONTH(@dt) = 2 
                THEN EOMONTH(@dt)
                ELSE DATEADD(DAY, 30 - DAY(@dt), @dt)
            END
        ELSE 
            DATEADD(MONTH, 1, DATEADD(DAY, 15 - DAY(@dt), @dt))
    END
END

步骤2:用递归CTE生成完整到期日计划

递归CTE会从第一期的已知到期日开始,逐期递推生成后续每一期的到期日:

WITH RecursiveInstallments AS (
    -- 锚点:取第一期的已有数据
    SELECT 
        instno,
        amount,
        duedate
    FROM YourTableName  -- 替换成你的实际表名
    WHERE instno = 1

    UNION ALL

    -- 递归:基于上一期的到期日生成当前期的到期日
    SELECT 
        t.instno,
        t.amount,
        dbo.duedategenerator(r.duedate) AS duedate
    FROM YourTableName t
    JOIN RecursiveInstallments r ON t.instno = r.instno + 1
    WHERE t.duedate IS NULL
)
SELECT * FROM RecursiveInstallments ORDER BY instno;

运行结果

执行后会得到你期望的输出:

instno | amount  | duedate
------------------------------
1      | 1000.00 | 2020-01-30
2      | 1000.00 | 2020-02-15
3      | 1000.00 | 2020-02-29
4      | 1000.00 | 2020-03-15
5      | 1000.00 | 2020-03-30

补充说明

  • 递归CTE的核心是逐期依赖:每一期的到期日都由前一期的结果计算而来,完美适配你的半月度摊销规则;
  • EOMONTH函数会自动处理闰年二月的月末日期(比如2020年二月返回29日),无需额外判断;
  • 如果你的分期编号不是连续的1、2、3...,可以调整递归连接的条件(比如用ROW_NUMBER()生成连续序号)。

内容的提问来源于stack exchange,提问作者Dekso

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.07 08:13:12