C#模糊逻辑贷款审批程序“所有隶属度为0”异常排查与解决
问题分析:Accord Fuzzy库贷款审批程序边界值异常解决
错误根源
你碰到的System.Exception异常(提示The numerical output in unavailable. All memberships are zero.),本质是输入的边界值没有被模糊隶属函数或规则覆盖:
- 比如Age=16是你设定的输入下限,但如果你的Age模糊子集(比如「年轻/中年/老年」)的隶属函数没覆盖到16——比如「年轻」的隶属函数从18才开始生效,那16对应的隶属度就是0;
- CreditScore=100作为上限,若「优秀」的隶属函数只到95,100的隶属度直接为0;
- Employment=10同理,要是「稳定就业」的隶属函数最高只到8,10的隶属度也是0。
当任何一个输入变量的所有模糊子集隶属度全为0时,模糊推理系统找不到可触发的规则,输出变量Approval也就没有任何隶属度数据,调用IS.Evaluate("Approval")自然会抛出异常。
解决办法
1. 调整隶属函数,覆盖完整输入范围
给每个输入变量的模糊子集设置覆盖全范围的隶属函数,确保边界值至少属于一个模糊子集:
- Age=16:把「年轻」的梯形隶属函数左边界设为16,比如
new TrapezoidalMembershipFunction(16, 16, 25, 35),这样16的隶属度直接为1; - CreditScore=100:让「优秀」的梯形隶属函数右边界到100,比如
new TrapezoidalMembershipFunction(80, 85, 90, 100),100的隶属度为1; - Employment=10:把「稳定就业」的三角形隶属函数顶点设为10,比如
new TriangularMembershipFunction(8, 10, 10),10的隶属度为1。
示例代码(Age变量):
var ageVar = new LinguisticVariable("Age", 16, 100); // 覆盖16-100全范围的三个模糊子集 ageVar.AddLabel("Young", new TrapezoidalMembershipFunction(16, 16, 25, 35)); ageVar.AddLabel("MiddleAged", new TrapezoidalMembershipFunction(30, 40, 55, 65)); ageVar.AddLabel("Old", new TrapezoidalMembershipFunction(60, 70, 100, 100));
2. 补充兜底模糊规则
就算隶属函数覆盖了范围,也可以加一条兜底规则,避免极端组合没规则匹配:
// 兜底规则:当输入处于边界时,输出中等审批值 var fallbackRule = new FuzzyRule( Antecedent.Construct( new FuzzyProposition(ageVar, ageVar.Labels["Young"]), new FuzzyProposition(creditScoreVar, creditScoreVar.Labels["Excellent"]) ), Consequent.Construct(new FuzzyProposition(approvalVar, approvalVar.Labels["Medium"])) ); // 把规则添加到推理系统 IS.AddRule(fallbackRule);
或者更通用的兜底:只要任意输入的隶属度异常,就给Approval一个默认模糊子集的映射。
3. 输入前置校验修正
在传入模糊系统前,先把输入值钳制在定义的范围内(防止边界外输入,同时确保边界值准确):
// 修正所有输入到合法范围 int age = Math.Clamp(inputAge, 16, 100); int creditScore = Math.Clamp(inputCreditScore, 0, 100); int employment = Math.Clamp(inputEmployment, 0, 10); // 再把修正后的值传入模糊系统 IS.SetInput("Age", age); IS.SetInput("CreditScore", creditScore); IS.SetInput("Employment", employment);
4. 检查规则完整性
逐一核对边界输入组合(比如Age=16+CreditScore=100+Employment=10),确保有对应的模糊规则触发,让输出变量能获得隶属度值。
总结
核心问题就是边界值未被模糊隶属函数或规则覆盖,导致隶属度全为0无法完成去模糊化。通过调整隶属函数、加兜底规则、输入校验这几步就能彻底解决这个问题。
内容的提问来源于stack exchange,提问作者user21132409
相关产品推荐
相关产品推荐

