手动实现Python感知机全输入输出相同值问题排查求助
感知机全量同输出故障排查
故障由以下几个核心编码错误直接导致,按影响优先级排序:
- 权重更新方向完全反转
感知机权重更新的核心逻辑是预测错误时,将权重向正确标签方向调整。正确误差定义为目标值 - 预测值,你的代码中写为prediction - target,误差符号完全相反,权重会随着训练往错误方向偏移,训练越久结果偏差越大。
修正误差计算代码:error = target - prediction - 训练轮次不足,模型未收敛
你当前仅对100个训练样本遍历了1次。感知机是迭代更新模型,需要多轮重复遍历整个训练集,直到连续一整轮预测无误差(收敛)才能停止训练,单轮遍历完全无法让权重调整到有效值。
可参考如下训练流程修正:# 最多迭代100轮,避免线性不可分场景下死循环 for _ in range(100): epoch_error = 0 for point in train_data: # 让train方法返回当前样本的误差值 sample_error = neuron.train(point.inputs, point.label) epoch_error += abs(sample_error) # 整轮无预测错误,提前终止训练 if epoch_error == 0: break - 标签编码与激活函数输出不匹配
你实现的sign激活函数输出为1和-1两类,必须保证训练集标签严格对应:x>y的正样本标签为1,x<=y的负样本标签为-1。如果标签用布尔值True/False或者0/1编码,误差计算会完全失真,直接导致权重更新逻辑失效。 - 激活函数逻辑存在冗余风险
当前激活函数用n == abs(n)做判断,可直接简化为n >= 0,避免极小负数、负零等极端值导致的判断异常,修正后代码:def sig(self, n): return 1 if n >= 0 else -1
优化建议
- 权重初始值建议设为
[-1, 1]区间的小随机数,不要全初始化为0,避免初始更新时所有权重同步变化,拖慢收敛速度 - 可在输入中增加一个固定值为1的偏置项,对应权重为偏置b,不仅能加快当前任务的收敛速度,还能适配不经过原点的分类分割线
内容的提问来源于stack exchange,提问作者Kavin Bharathi
相关产品推荐
相关产品推荐

