Rule Based: Syntax Tree
设计语法:
import random
#一个“接待员”的语言可以定义为
host = """
host = 寒暄 报数 询问 业务相关 结尾
报数 = 我是 数字 号 ,
数字 = 单个数字 | 数字 单个数字
单个数字 = 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9
寒暄 = 称谓 打招呼 | 打招呼
称谓 = 人称 ,
人称 = 先生 | 女士 | 小朋友
打招呼 = 你好 | 您好
询问 = 请问你要 | 您需要
业务相关 = 玩玩 具体业务
玩玩 = null
具体业务 = 喝酒 | 打牌 | 打猎 | 赌博
结尾 = 吗?
"""
def create_grammar(grammar_str, spl=' /= ', line_split='\n'):
grammar = {}
for line in grammar_str.split(line_split):
if not line.strip(): continue
line_splited = line.split('=')
exp, stmt = line_splited
grammar[exp.strip()] = [s.split() for s in stmt.split('|')]
return grammar
grammar = create_grammar(host,"host")
print(grammar)
运行结果:
{
'host': [['寒暄', '报数', '询问', '业务相关', '结尾']],
'报数': [['我是', '数字', '号', ',']],
'数字': [['单个数字'], ['数字', '单个数字']],
'单个数字': [['1'], ['2'], ['3'], ['4'], ['5'], ['6'], ['7'], ['8'], ['9']],
'寒暄': [['称谓', '打招呼'], ['打招呼']],
'称谓': [['人称', ',']], '人称': [['先生'], ['女士'], ['小朋友']],
'打招呼': [['你好'], ['您好']],
'询问': [['请问你要'], ['您需要']], '业务相关': [['玩玩', '具体业务']],
'玩玩': [['null']],
'具体业务': [['喝酒'], ['打牌'], ['打猎'], ['赌博']],
'结尾': [['吗?']]
}
后面value里面的内容如果是字典的key就继续迭代检索,不是就停止、输出。
choice = random.choice
def generate(gram, target):
if target not in gram: return target # means target is a terminal expression
expaned = [generate(gram, t) for t in choice(gram[target])]
return ''.join([e if e != '/n' else '\n' for e in expaned if e != 'null'])
案例小结:
import random
#一个“接待员”的语言可以定义为
host = """
host = 寒暄 报数 询问 业务相关 结尾
报数 = 我是 数字 号 ,
数字 = 单个数字 | 数字 单个数字
单个数字 = 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9
寒暄 = 称谓 打招呼 | 打招呼
称谓 = 人称 ,
人称 = 先生 | 女士 | 小朋友
打招呼 = 你好 | 您好
询问 = 请问你要 | 您需要
业务相关 = 玩玩 具体业务
玩玩 = null
具体业务 = 喝酒 | 打牌 | 打猎 | 赌博
结尾 = 吗?
"""
def create_grammar(grammar_str, split='=>', line_split='\n'):
grammar = {}
for line in grammar_str.split(line_split):
if not line.strip(): continue
exp, stmt = line.split(split)
grammar[exp.strip()] = [s.split() for s in stmt.split('|')]
return grammar
choice = random.choice
def generate(gram, target):
if target not in gram: return target # means target is a terminal expression
expaned = [generate(gram, t) for t in choice(gram[target])]
return ''.join([e if e != '/n' else '\n' for e in expaned if e != 'null'])
for i in range(20):
print(generate(gram=create_grammar(host, split='='), target='host'))
运行结果
你好我是68号,您需要打猎吗?
你好我是1号,请问你要赌博吗?
小朋友,你好我是2号,请问你要打牌吗?
先生,你好我是268号,请问你要喝酒吗?
小朋友,你好我是8号,请问你要打猎吗?
女士,您好我是986号,请问你要喝酒吗?
先生,你好我是3号,请问你要喝酒吗?
您好我是389号,请问你要打牌吗?
小朋友,您好我是9号,请问你要打猎吗?
女士,你好我是3号,请问你要喝酒吗?
先生,您好我是75号,请问你要打牌吗?
小朋友,你好我是4号,您需要赌博吗?
女士,你好我是9号,请问你要赌博吗?
小朋友,您好我是92号,请问你要打牌吗?
您好我是3号,您需要打牌吗?
你好我是64号,您需要打牌吗?
先生,你好我是4号,请问你要赌博吗?
您好我是6693号,您需要喝酒吗?
你好我是4781797号,请问你要喝酒吗?
你好我是873662114号,您需要赌博吗?