多项式拟合正弦曲线:机器学习入门实验,理解过拟合与正则化

发布时间:2026/10/3 13:45:33

多项式拟合正弦曲线:机器学习入门实验,理解过拟合与正则化 简介这份资源面向机器学习初学者与课程实验学习者围绕多项式拟合正弦曲线这一经典课题提供完整的Python实现与实验报告。内容涵盖最小二乘法解析解、带2范数惩罚项的正则化优化、梯度下降与共轭梯度法的手写实现并引导读者通过调整数据量、超参数与多项式阶数直观理解过拟合现象及其克服方法。资源包共4个文件包含3个py源码与1份doc实验报告压缩包约581KB源码按数据生成、最小二乘求解、梯度下降等模块拆分注释详尽便于对照实验报告逐步复现。目前已有183人学习下载。读者可借此掌握从数据加噪、模型拟合到优化求解的完整流程理解无正则与有正则损失函数的差异并学会在不依赖自动微分框架的前提下自行推导梯度、编写迭代优化代码适合作为课程作业参考或自学练手材料。1. 多项式拟合正弦曲线为什么它是机器学习入门最值得亲手跑一遍的实验多项式拟合正弦曲线是很多人翻开《机器学习》或吴恩达课程后遇到的第一个能看见结果的实验。它不依赖真实数据集不需要爬虫也不用配置复杂环境只要 Python 加 NumPy、Matplotlib 就能跑通。但恰恰是这个小实验把机器学习里最核心的几个概念——模型容量、欠拟合、过拟合、训练集与验证集、正则化——全部串在了一起。正弦曲线本身是光滑的周期函数用多项式去逼近它阶数低了拟合不上阶数高了在两端疯狂震荡这种肉眼可见的翻车是任何教科书插图都替代不了的。这篇笔记面向的是想真正动手复现一遍的读者从环境搭建、数据生成、模型训练到画出对比图、看懂误差曲线再到把代码整理成一份能交的实验报告。如果你正在准备机器学习期末复习或者刚学完 Python 想找个练手项目这个实验的性价比非常高。2. 先把数学讲透多项式拟合正弦曲线到底在拟合什么2.1 从泰勒展开到最小二乘多项式为什么能逼近正弦正弦函数在数学上可以展开成无穷级数去掉高阶项之后就是一个多项式。这给了我们一个直觉只要阶数足够多项式能在一定区间内逼近正弦曲线。但机器学习里的做法不是去算泰勒系数而是把问题转化成给定一批带噪声的观测点找一组多项式系数让预测值和真实值差距最小。形式化地设多项式为y w0 w1·x w2·x² ... wM·x^M其中 M 是阶数w 是待求系数。我们手上有一批训练样本 (x_i, t_i)t_i 是带噪声的目标值。目标是最小化平方误差E(w) 1/2 · Σ (y(x_i, w) - t_i)²这是一个标准的线性最小二乘问题。虽然它对 x 是非线性的因为有 x²、x³但对系数 w 是线性的所以可以直接求解析解也可以用梯度下降。解析解的形式是w (XᵀX)⁻¹ Xᵀt其中 X 是范德蒙德矩阵每一行是 [1, x_i, x_i², ..., x_i^M]。这个公式在阶数不高、数据量不大时非常稳定也是很多入门代码直接用的方式。理解这一点很关键多项式拟合正弦曲线不是神经网络它没有隐藏层、没有激活函数本质是一个线性回归模型套了一层特征变换。你把 x 扩展成 [1, x, x², ..., x^M]剩下的就是普通线性回归。这也是为什么它适合入门——所有复杂度都来自特征工程选阶数而不是模型结构本身。2.2 阶数 M 是唯一的超参数欠拟合与过拟合的分界线在这个实验里唯一需要你手动决定的超参数就是阶数 M。M 太小模型表达能力不够曲线太平拟合不上正弦的起伏这叫欠拟合。M 太大模型开始记住训练数据里的噪声曲线在数据点之间剧烈震荡尤其在区间两端会飞出天际这叫过拟合。常见的观察结果是M0 和 M1 明显欠拟合M3 已经能大致跟上正弦的形状M9 在训练点上几乎完美但两端开始翘M15 以上基本就是灾难现场。这个从欠拟合到刚好再到过拟合的过程是理解模型容量最直观的方式。但要注意过拟合不是单纯由 M 决定的它和训练样本数量也强相关。同样的 M9如果只有 10 个训练点过拟合会非常严重如果有 100 个点可能看起来还不错。所以这个实验真正想让你体会的是模型复杂度要和数据量匹配。2.3 训练误差下降不代表模型变好验证集的作用如果你只画训练误差随 M 变化的曲线会发现它几乎单调下降——M 越大训练误差越小M 足够大时甚至能降到接近零。但这不代表模型变好了只代表它把训练数据背下来了。正确做法是留出一部分数据作为验证集或测试集同时观察训练误差和验证误差。典型曲线是训练误差一直降验证误差先降后升那个最低点对应的 M 就是相对合理的阶数。这条U 形曲线是机器学习里最经典的图之一也是这个实验报告里必须呈现的内容。在实际写代码时我一般会生成两批数据一批用于训练一批用于验证两批都加同样的高斯噪声。然后对每个 M 分别训练、分别计算两边的均方误差最后画在一张图上。3. 用 Python 从零跑通数据生成、模型训练与可视化3.1 环境准备与依赖安装这个实验对环境的依赖非常轻只需要 Python 3.8 以上加上 NumPy 和 Matplotlib。如果你还没装 Python去官网下载安装包即可安装时记得勾选Add Python to PATH。装好之后在命令行里执行pip install numpy matplotlib如果你用 VS Code建议同时装一下 Python 扩展这样可以直接在编辑器里运行和调试。不需要 sklearn也不需要 PyTorch这个实验用纯 NumPy 就能完成反而更能看清每一步在做什么。提示如果你后续想对比 sklearn 的 PolynomialFeatures LinearRegression也可以装 scikit-learn但建议先用 NumPy 手写一遍理解矩阵构造过程。3.2 生成带噪声的正弦数据先写数据生成部分。核心是在 [0, 2π] 区间内均匀取点计算 sin 值再加上高斯噪声。import numpy as np import matplotlib.pyplot as plt # 固定随机种子保证每次运行结果一致 np.random.seed(42) # 生成训练数据20 个点均匀分布在 [0, 2π] N_train 20 x_train np.linspace(0, 2 * np.pi, N_train) # 真实正弦值 高斯噪声均值 0标准差 0.3 t_train np.sin(x_train) np.random.normal(0, 0.3, N_train) # 生成验证数据另外 20 个点位置稍微错开 N_val 20 x_val np.linspace(0, 2 * np.pi, N_val) 0.05 t_val np.sin(x_val) np.random.normal(0, 0.3, N_val) # 用于画真实曲线的密集点 x_plot np.linspace(0, 2 * np.pi, 200) y_plot np.sin(x_plot)这段代码里有两个参数值得注意。一个是噪声标准差 0.3它决定了数据点偏离正弦的程度噪声越大过拟合越容易发生。另一个是训练点数量 20这个数量对 M9 来说偏少正好能制造出明显的过拟合现象。如果你想观察数据量对过拟合的影响可以把 N_train 改成 100 再跑一次对比 M9 的曲线形状。验证集的 x 坐标我特意加了 0.05 的偏移避免和训练点完全重合这样验证误差更能反映模型在没见过的位置上的表现。3.3 构造范德蒙德矩阵并求解系数接下来是核心部分给定阶数 M构造特征矩阵并求系数。def fit_polynomial(x, t, M): 用最小二乘法拟合 M 阶多项式 x: 输入坐标形状 (N,) t: 目标值形状 (N,) M: 多项式阶数 返回: 系数向量 w形状 (M1,) # 构造范德蒙德矩阵每一列是 x 的 0 到 M 次幂 X np.vander(x, M 1, increasingTrue) # 最小二乘解析解w (X^T X)^(-1) X^T t # 用 lstsq 比直接求逆更稳定 w, _, _, _ np.linalg.lstsq(X, t, rcondNone) return w def predict_polynomial(x, w): 用求得的系数预测 M len(w) - 1 X np.vander(x, M 1, increasingTrue) return X w这里用np.linalg.lstsq而不是手动求逆是因为当 M 较大时XᵀX 可能接近奇异直接求逆数值不稳定。lstsq内部用 SVD 分解能给出更可靠的结果。np.vander的increasingTrue表示列的顺序是从 x⁰ 到 x^M和我们的公式一致。如果你手动实现求逆版本可以写成w np.linalg.inv(X.T X) X.T t但在 M15 以上时可能会看到明显的数值误差甚至报奇异矩阵错误。这也是一个值得在实验报告里提一句的坑。3.4 画出不同阶数的拟合曲线对比图有了拟合和预测函数就可以批量跑不同阶数并画图了。fig, axes plt.subplots(2, 2, figsize(12, 8)) M_list [1, 3, 9, 15] for ax, M in zip(axes.ravel(), M_list): w fit_polynomial(x_train, t_train, M) y_pred predict_polynomial(x_plot, w) ax.scatter(x_train, t_train, colorred, s20, label训练数据) ax.plot(x_plot, y_plot, g--, label真实 sin(x)) ax.plot(x_plot, y_pred, b-, labelfM{M} 拟合) ax.set_ylim(-2, 2) ax.legend() ax.set_title(f多项式阶数 M{M}) plt.tight_layout() plt.show()运行后你会看到四张子图。M1 是一条直线完全跟不上正弦M3 已经能看出正弦的轮廓M9 在训练点上贴合得很好但两端开始有轻微上翘M15 则在两端剧烈震荡甚至超出了 y 轴范围。这个对比图是实验报告里最有说服力的部分。set_ylim(-2, 2)是为了让四张图尺度一致方便对比。如果你发现 M15 的曲线飞出太远可以适当放宽范围但那样其他图就看不清了所以固定范围更好。3.5 计算训练误差与验证误差并画 U 形曲线最后一步是把误差量化画出误差随 M 变化的曲线。def mse(x, t, w): 均方误差 y_pred predict_polynomial(x, w) return np.mean((y_pred - t) ** 2) M_range range(0, 16) train_errors [] val_errors [] for M in M_range: w fit_polynomial(x_train, t_train, M) train_errors.append(mse(x_train, t_train, w)) val_errors.append(mse(x_val, t_val, w)) plt.figure(figsize(8, 5)) plt.plot(M_range, train_errors, o-, label训练误差) plt.plot(M_range, val_errors, s-, label验证误差) plt.xlabel(多项式阶数 M) plt.ylabel(均方误差) plt.yscale(log) # 对数坐标因为误差跨度大 plt.legend() plt.grid(True) plt.show()这张图通常会呈现训练误差随 M 增大持续下降验证误差先降后升在 M3 到 M6 之间有一个低谷。yscale(log)是为了让误差跨度大的时候也能看清趋势如果你觉得对数坐标不直观也可以改成线性坐标但 M15 的验证误差可能会把其他点压扁。到这里一个完整的多项式拟合正弦曲线实验就跑通了。代码总量不到 80 行但覆盖了数据生成、模型定义、训练、评估、可视化全流程。4. 避坑与排查这个实验里最容易翻车的 5 个地方4.1 现象M15 时程序报奇异矩阵错误或系数异常大原因直接用np.linalg.inv(X.T X)求逆时高阶范德蒙德矩阵的条件数非常大XᵀX 接近奇异数值误差被放大。解决改用np.linalg.lstsq它内部用 SVD 分解对病态矩阵更鲁棒。如果坚持用求逆可以加一个很小的正则项也就是岭回归的思路w inv(X.T X λI) X.T tλ 取 1e-6 到 1e-3 之间。4.2 现象每次运行结果都不一样曲线形状变化很大原因没有固定随机种子每次生成的噪声不同训练数据就不同。解决在生成数据前加np.random.seed(42)。如果你想让实验报告更严谨可以跑多次取平均误差但入门阶段固定种子就够了。4.3 现象验证误差曲线一直下降没有出现 U 形原因可能是验证集和训练集来自同一批点或者验证集太小、噪声太低。也可能是 M 的范围不够大还没进入过拟合区域。解决确认验证集的 x 坐标和训练集不完全重合把 M 范围扩大到 20 甚至 25适当增大噪声标准差让过拟合更容易出现。4.4 现象M9 的曲线看起来很好但 M15 也没有明显过拟合原因训练点数量太多比如 N_train100此时 M15 相对数据量来说并不算高。解决这其实不是 bug而是说明模型复杂度和数据量要匹配。如果你想看到明显过拟合把 N_train 降到 10 到 15 之间再试。4.5 现象画图时中文显示成方框原因Matplotlib 默认字体不支持中文。解决在画图前设置字体例如plt.rcParams[font.sans-serif] [SimHei]或者直接把图里的标签改成英文。如果是在 Linux 或 Mac 上SimHei 可能不存在可以换成Arial Unicode MS或DejaVu Sans。5. 把实验写成报告结构、图表与一个进阶技巧一份能交的机器学习实验报告核心不是代码有多长而是能不能把现象—原因—结论这条线讲清楚。我一般会按这个结构组织实验目的、实验原理、实验环境、实验步骤、实验结果与分析、实验结论。其中实验结果与分析是重点要放三张图不同阶数的拟合曲线对比图、训练误差与验证误差随 M 变化的曲线图、以及一组最优 M 下的拟合效果图。在写分析时不要只写M3 最好要写出依据验证误差在 M3 时取得最小值同时训练误差和验证误差差距不大说明没有明显过拟合。再对比 M15训练误差很小但验证误差很大两者差距悬殊说明模型记住了噪声。这种用数据说话的写法比单纯描述曲线形状更有说服力。如果你想让报告更有深度可以加一个进阶实验固定 M9改变训练样本数量比如 10、20、50、100观察验证误差的变化。你会发现随着数据量增加同一个 M 的过拟合程度会减轻。这个实验能直观说明数据量是抵抗过拟合的第一道防线。另一个值得尝试的技巧是加 L2 正则化。在损失函数里加一项 λ·||w||²然后观察不同 λ 下 M9 的拟合曲线。λ 很小时曲线仍然震荡λ 适中时曲线变得平滑λ 很大时曲线又变得过于平坦。这个对比能帮你理解正则化系数的作用也是很多机器学习课程里的经典练习。我自己做这个实验时最大的教训是一开始只盯着训练误差看觉得 M 越大越好结果画出来的曲线在两端飞得离谱还以为是代码写错了。后来才明白训练误差小不等于模型好验证集才是照妖镜。这个习惯后来一直跟着我——不管做什么模型先留验证集再看训练误差和验证误差的差距。希望帮到你。本文还有配套的精品资源点击获取
延伸阅读

更多相关文章

2026/10/3 13:40:33

FaceFusion 离线部署指南:四步在内网跑通 AI 换脸

FaceFusion 离线部署指南:四步在内网跑通 AI 换脸 【免费下载链接】facefusion Industry leading face manipulation platform 项目地址: https://gitcode.com/GitHub_Trending/fa/facefusion FaceFusion 是一款支持换脸、人脸增强、年龄修改的 AI 面部处理平…

2026/10/3 14:40:35

保险核心系统实时化:Flink 实战从数据接入到生产避坑

简介:这是一份面向大数据开发初学者与进阶工程师的Flink实战项目资料,基于保险行业真实业务场景,采用FlinkHBaseKafkaPhoenix架构,实现业务系统数据库数据的实时同步与实时统计报表分析,适合想通过完整项目理解流式计算…

2026/10/3 14:40:35

SSM与Flask协同:古诗词展演系统全栈设计与实现

前些年帮朋友做毕业设计,接触过不少文化展示类项目,大多是套个后台管理系统、配个增删改查界面,做完就完事。但这次拿到“基于JavaSSMFlask古诗词展演系统”这个题目时,我却觉得有点意思——它不是让你纯粹做管理,而是…

2026/10/3 14:40:35

考研互助平台全栈开发:SpringBoot+Vue+MyBatis从设计到部署

1. 项目整体设计与技术选型做考研互助交流平台这个项目,我最初的想法其实很简单:考研人群的需求非常集中,无非是找资料、找学长学姐答疑、看经验分享、找研友一起打卡。但这些需求目前散落在各类论坛、QQ群、公众号里,信息非常割裂…

2026/10/3 14:40:35

SpringBoot在线教学平台毕业设计实战:架构、部署与避坑

1. 毕设选题与整体架构拆解1.1 在线教学平台到底做什么:从需求拿捏项目形态“基于 SpringBoot 的在线教学平台”这类题目在计算机毕业设计里属于出镜率极高的类型,但大家拿到的原始需求往往只有一句话:做一个支持课程管理、教学资源上传下载、…

2026/10/3 14:40:35

YuE2白盒音乐生成:从抽卡玄学到工程化创作

1. 这不是“抽卡”,是把音乐生成从黑盒赌徒变成白盒工程师 最近在几个AI音乐社群里,总看到有人发截图:“又抽了37次才出想要的副歌!”底下一片“懂的都懂”“命硬才能出神曲”。我盯着那张满屏红色失败提示的界面,突然…

2026/10/3 14:35:35

hindsight与Agent Memory:从记忆分层到MCP+Docker工程实践

1. 从“hindsight”这个词说起:为什么它值得单独拿出来聊“hindsight”这个词本身的意思是“事后聪明”,也就是我们常说的“事后诸葛亮”。但放在当前的技术语境里,它指向的是一个非常具体、也非常要命的问题:智能体(A…

2026/10/2 8:16:46

东莞市品牌网站建设报价常见报错与解决

东莞品牌网站建设报价单背后:一份保姆级建站教程避坑实录 网站做好了没人访问,这大概是很多老板最头疼的事。花了大几万做的品牌站,上线后流量惨淡,比路边摊还冷清。别急着骂外包公司,很多“东莞品牌网站建设报价”里藏着不少猫腻,比如用模板站冒充定制…

2026/10/2 18:20:53

如何划分训练/验证集:Spirula Studio五种eval_mode策略详解

如何划分训练/验证集:Spirula Studio五种eval_mode策略详解 【免费下载链接】spirula-studio Cross-vendor 3D Gaussian Splatting trainer - video to splat to mesh, Vulkan or CUDA. 项目地址: https://gitcode.com/GitHub_Trending/sp/spirula-studio Sp…

2026/10/1 10:48:55

SEO怎么推广速查手册新手避坑实战指南

SEO怎么推广速查手册新手避坑实战指南 模板网站太丑不够用?别急着加滤镜,那是治标不治本。很多老板盯着后台流量掉得眼红,却还在纠结首页Banner的圆角是不是3像素。这就像穿着西装去挖土,姿势不对,努力白费。我整理这份 速查手册…

2026/10/3 0:04:31

国内大学生必备的AI写作辅助软件是哪款?

国内高校学生在论文写作过程中,越来越依赖AI辅助工具提升效率,主流方案以本土化全流程工具为核心,结合通用大模型与专业插件,覆盖选题构思、框架搭建、初稿撰写、查重降重、格式调整等关键环节,本文将深入解析当前主流…

2026/10/3 0:04:31

Codex接入Jev模型完整指南:配置方法、本地部署与踩坑排查

最近不少人在讨论 Codex 搭配 Jev 这套玩法,我一开始没太当回事,直到自己把 Jev 接进 Codex跑了几轮编码任务之后,才明白那些说“直接起飞”的人是怎么想的。Codex 作为工具本身已经够能打了,但模型固定、上下文策略固定&#xff…

2026/10/3 0:04:31

GitHub 热门: NVIDIA/Model-Optimizer

👋 Hi,我擅长 AI 大模型应用落地、意识解码与 AI 开发工具链 。 💡 创业路上,用技术换时间,一起把 AI 变成生产力 🚀 >GitHub 热门: NVIDIA/Model-Optimizer 凌晨两点,你刚把跑通了的 Qwen3.…

还想了解更多?直接咨询顾问

免费诊断 + 免费方案 + 透明报价。

全国咨询热线400-8866-253
免费获取方案
☎咨询二维码 ☎ ↑