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

Python如何优雅控制用户提问流 支持答案校验与分支跳转逻辑

实现方案

你完全可以沿用字典定义提问流的设计,不需要写大量冗余的if判断,只要给需要校验的问题节点增加校验规则配置即可,整体逻辑依然保持好维护、易扩展的特性。

核心改造思路

  • 单独写通用的校验函数,覆盖日期校验、合法选项校验这类重复用到的场景
  • 给需要校验的字典节点增加校验相关的配置字段,和原有Y/N类固定选项的跳转逻辑兼容
  • 写一套通用的提问主循环,自动根据当前节点的配置决定是直接匹配跳转还是先做输入校验

通用校验函数实现

首先写两个你现在需要用到的校验函数,后续有新的校验需求新增对应函数即可:

from datetime import datetime

# 校验输入是否为合法DD/MM/YYYY格式日期
def validate_date(input_str):
    try:
        datetime.strptime(input_str.strip(), "%d/%m/%Y")
        return True
    except ValueError:
        return False

# 校验输入是否在指定的合法选项列表中
def validate_options(input_str, valid_options):
    return input_str.strip().upper() in valid_options

改造后的提问流字典

你原来的字典只要微调需要校验的三个节点即可,其余节点完全不用改:

stopquestions = {
    'stopconfirm':
        {
            'prompt':'是否要执行该操作? Y/N ',
            'Y':'prev',
            'N':'genericerror'
        },
    'prev':
        {
            'prompt':'之前是否完成过? Y/N ',
            'Y':'bamerch',
            'N':'frequency1'
        },
    'bamerch':
        {
            'prompt':'操作对象是B还是M? B/M ',
            'B':'candate',
            'M':'candate'
        },
    'candate':
        {
            'prompt':'请输入对应日期,格式为DD/MM/YYYY:',
            'validator': validate_date, # 绑定日期校验函数
            'valid_next': 'length', # 校验通过跳转到的节点
            'invalid_next': 'genericerror' # 校验不通过跳转到的节点
        },
    'length':
        {
            'prompt':'关于时长的问题是否符合? Y/N ',
            'Y':'frequency2',
            'N':'frequency2'
        },
    'frequency1':
        {
            'prompt':'请选择频率:W/F/M/Q/A ',
            'validator': lambda x: validate_options(x, ['W','F','M','Q','A']), # 绑定选项校验,指定合法值
            'valid_next': 'dis',
            'invalid_next': 'genericerror'
        },
    'frequency2':
        {
            'prompt':'请选择频率:W/F/M/Q/A ',
            'validator': lambda x: validate_options(x, ['W','F','M','Q','A']),
            'valid_next': 'end',
            'invalid_next': 'genericerror'
        },
    'dis':
        {
            'prompt':'是否与最近的记录存在分歧? Y/N ',
            'Y':'end',
            'N':'end'
        },
    'genericerror':
        {
            'text':'输入不合法,请重新进入流程。',
            'action':'end'
        }
}

通用提问主循环

这套逻辑写完之后,后续新增问题只要改字典就行,不用动循环逻辑:

def run_question_flow(start_node='stopconfirm'):
    current_node = start_node
    answers = {} # 存储所有用户的回答,后续给决策矩阵用
    while current_node != 'end':
        node_config = stopquestions[current_node]
        # 如果是提示类节点比如错误页,先打印内容再跳转
        if 'text' in node_config:
            print(node_config['text'])
            current_node = node_config['action']
            continue
        # 提问获取用户输入
        user_input = input(node_config['prompt']).strip().upper()
        answers[current_node] = user_input
        # 判断当前节点有没有校验器,有就先走校验逻辑
        if 'validator' in node_config:
            if node_config['validator'](user_input):
                current_node = node_config['valid_next']
            else:
                current_node = node_config['invalid_next']
        # 没有校验器的就按原有固定选项匹配跳转
        else:
            current_node = node_config.get(user_input, 'genericerror')
    print('提问结束,收集到的回答:', answers)
    # 后续你可以在这里加决策矩阵的逻辑,用answers字典匹配要执行的操作
    return answers

# 启动提问
if __name__ == '__main__':
    run_question_flow()

扩展说明

后续如果要加新的校验场景,比如校验手机号、校验数字范围,只要新增对应的校验函数,然后在问题节点里绑定即可,不用修改主逻辑,完全符合你易扩展的需求。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.30 14:06:03