资讯动态

基于MATLAB的圆孔菲涅尔衍射仿真:从物理模型到代码实现与验证

发布时间:2026/10/9 19:14:58 来源:尧图企业网站定制
1. 从一次仿真翻车说起为什么圆孔衍射值得动手算一遍刚接触光学仿真那会儿我对圆孔菲涅尔衍射的理解长期停留在课本上那条公式和一张黑白相间的同心圆环图上。直到有一次需要给一个成像系统做杂散光评估我才发现真正把圆孔衍射算对、算稳、算得能指导工程决策和考试里套公式完全是两码事。那次我用一个想当然的采样密度去算近场衍射结果中心亮斑的能量分布明显失真边缘还出现了莫名其妙的锯齿排查了大半天才意识到是采样和传播距离的匹配出了问题。这篇文章就是围绕基于MATLAB的圆孔菲涅尔衍射这个主题把从物理模型到代码落地、从参数选择到结果验证的完整链路讲清楚。它适合三类人正在做光学课程设计或仿真作业的学生、需要快速搭建衍射计算原型的研究人员以及想把衍射效应纳入系统评估的工程从业者。核心要解决的问题有三个——菲涅尔衍射到底在算什么、MATLAB里怎么把它算准、算完之后怎么判断结果可不可信。关键词我先摆出来菲涅尔衍射、圆孔衍射、MATLAB仿真、基尔霍夫衍射、菲涅尔近似、采样定理、快速傅里叶变换、衍射光强分布。这些词基本覆盖了从理论到实现的全部关键节点。下面我会按物理图像—数值方法—代码实现—结果验证—工程延伸的顺序展开中间穿插我自己踩过的坑和实测有效的处理技巧。你不需要有很深的数学功底但需要愿意跟着把每一步的为什么想明白。2. 菲涅尔衍射的物理图像近场里光到底怎么拐弯2.1 从惠更斯原理到菲涅尔-基尔霍夫积分要理解圆孔菲涅尔衍射得先接受一个反直觉的事实光并不是只沿直线传播。惠更斯原理告诉我们波前上的每一点都可以看作一个新的次级波源这些次级波源发出的球面波相互干涉就决定了后续波场的分布。菲涅尔在这个思想上加了相干叠加的权重基尔霍夫又用格林函数把它严格化最终得到菲涅尔-基尔霍夫衍射积分$$U(P) \frac{1}{j\lambda}\iint_{\Sigma} U_0(Q)\frac{e^{jkr}}{r}K(\chi),dS$$这里 $U_0(Q)$ 是孔径面上的复振幅$r$ 是孔径上点到观察点的距离$K(\chi)$ 是倾斜因子$\lambda$ 是波长。这个积分是理解一切衍射现象的起点但直接算它非常费劲因为每个观察点都要对整个孔径做面积分。菲涅尔近似做的事情是把 $r$ 在孔径尺寸远小于传播距离的假设下做泰勒展开保留到二次项。这一步的物理含义是我们不再精确追踪每条光线的几何路径而是用抛物面波近似球面波。近似成立的条件是传播距离 $z$ 满足 $z^3 \gg \frac{\pi}{4\lambda}\left[(x-x)^2(y-y)^2\right]^2_{max}$通俗说就是观察面不能离孔径太近也不能让孔径相对太大。2.2 菲涅尔区理解近场明暗交替的钥匙菲涅尔衍射最迷人的地方是轴上光强会随传播距离出现明暗交替。这背后是菲涅尔半波带的概念。把孔径对轴上观察点划分成若干个半波带相邻波带到观察点的光程差为半个波长因此相邻波带贡献的复振幅方向相反。当孔径恰好包含奇数个半波带时轴上光强出现极大包含偶数个时出现极小。这个图像解释了一个经典现象圆孔衍射在近场轴上会出现中心亮、暗交替的区域而不是像远场那样单调地衰减。菲涅尔数 $N_F a^2/(\lambda z)$$a$ 为圆孔半径就是描述这个区域的关键无量纲量。$N_F$ 大意味着处于近场、半波带数量多、轴上振荡剧烈$N_F$ 小则逐渐过渡到夫琅禾费远场。我在实际计算里养成了一个习惯动手写代码前先估一下 $N_F$。如果 $N_F$ 在 1 到 10 之间轴上振荡会非常明显采样必须足够密如果 $N_F$ 远小于 1其实已经接近远场用夫琅禾费近似反而更省事也更稳。这个预判能帮你少走很多弯路。2.3 圆孔为什么是理解衍射的最佳起点圆孔之所以成为衍射教学和仿真的经典对象是因为它同时具备两个优点几何形状有解析对称性衍射图样有明确的物理特征。圆孔的夫琅禾费衍射给出艾里斑第一暗环半径满足 $1.22\lambda z/D$而菲涅尔区的圆孔衍射则呈现中心亮暗交替加外围同心环的结构。这种既有解析参照、又有丰富结构的特性让它成为验证数值算法是否正确的理想试金石。从工程角度看圆孔衍射直接对应大量真实场景圆形光阑、圆形孔径的成像系统、激光束的圆形截断、望远镜入瞳等。把圆孔算明白了换成矩形孔、环形孔、甚至带像差的孔径方法论是相通的。所以这个题目看似基础实则是衍射数值计算的基本功。3. 数值实现路线选择为什么我最终选了角谱法3.1 三种主流方法的对比与取舍在MATLAB里算菲涅尔衍射常见有三条路直接积分法、菲涅尔衍射的卷积法也叫直接法、以及角谱传播法。它们各有适用边界选错了要么慢得离谱要么结果失真。方法核心思想优点局限适用场景直接积分法对每个观察点做孔径面积分物理直观、易理解计算量 $O(N^4)$极慢小尺寸、教学演示菲涅尔卷积法用菲涅尔核做卷积借助FFT速度快、实现简单采样窗口固定近场易混叠中等距离、中等孔径角谱传播法在频域乘以传递函数精度高、距离灵活需处理频域采样和混叠近场到远场通用我最初用的是菲涅尔卷积法因为它代码短、跑得快。但很快发现一个问题当传播距离比较小、孔径相对较大时卷积核在空域的采样会严重不足结果出现明显的混叠伪影。后来改用角谱法虽然要多处理一些频域细节但稳定性和精度都上了一个台阶。3.2 角谱法的物理逻辑把光场拆成平面波角谱法的核心思想非常优雅任何光场都可以分解成一系列不同方向传播的平面波每个平面波在传播距离 $z$ 后只改变一个相位因子。具体来说对孔径面的复振幅做二维傅里叶变换得到角谱 $A(f_x, f_y)$然后乘以传播传递函数$$H(f_x, f_y) \exp\left(j 2\pi z \sqrt{\frac{1}{\lambda^2} - f_x^2 - f_y^2}\right)$$再逆傅里叶变换回空域就得到观察面的光场。当 $f_x^2 f_y^2 1/\lambda^2$ 时根号内为负对应倏逝波其幅度随距离指数衰减在传播计算中通常直接置零。这个方法的妙处在于它没有做菲涅尔的抛物面近似而是保留了完整的传播相位因此在近场和远场都成立。代价是要小心频域采样避免传递函数在频域边界处出现剧烈振荡导致的混叠。3.3 采样定理决定成败的那条隐形红线无论用哪种方法采样都是绕不开的坎。对圆孔衍射孔径面的采样间隔 $\Delta x$ 必须足够小才能准确描述圆孔的边缘。圆孔边缘是硬边其频谱是无限宽的理论上无法完全采样但工程上要求至少让第一暗环或主要环结构落在采样范围内。一个实用的经验判据是孔径面采样点数 $N$ 和采样间隔要满足 $\Delta x \leq \lambda z / (2 L)$ 之类的约束$L$ 为观察面尺寸同时观察面的采样要能分辨最细的衍射环。我通常的做法是先按物理尺寸确定观察窗口再反推需要的采样点数最后用 $N$ 取 2 的整数次幂如 1024、2048来配合FFT。注意采样不足最典型的表现是衍射环出现摩尔纹或规则锯齿而不是平滑的环。看到这种图案第一反应应该是加采样而不是怀疑物理模型。4. MATLAB代码逐段拆解从参数设定到光强输出4.1 参数初始化每个数字都要有物理依据先看参数设定部分。这段代码看起来简单但每个参数都直接影响结果是否可信。% 基本物理参数 lambda 632.8e-9; % 波长氦氖激光典型值 k 2*pi/lambda; % 波数 a 0.5e-3; % 圆孔半径0.5 mm z 0.3; % 传播距离0.3 m % 采样参数 N 2048; % 采样点数2的幂便于FFT L 5e-3; % 孔径面物理尺寸5 mm dx L/N; % 采样间隔 x (-N/2:N/2-1)*dx; % 坐标轴 [X, Y] meshgrid(x, x);这里有几个关键决策。波长选 632.8 nm 是因为它是常见激光波长便于和实验对照。圆孔半径 0.5 mm、传播距离 0.3 m算一下菲涅尔数 $N_F a^2/(\lambda z) (0.5\times10^{-3})^2/(632.8\times10^{-9}\times0.3) \approx 1.32$正好落在菲涅尔衍射特征明显的区间适合观察轴上振荡。采样点数取 2048 是权衡的结果1024 在 $L5$ mm 时 $\Delta x \approx 4.9\ \mu m$对圆孔边缘的描述偏粗2048 时 $\Delta x \approx 2.4\ \mu m$边缘更平滑同时单次FFT在普通笔记本上也就零点几秒完全可接受。孔径面尺寸 $L$ 要明显大于孔径直径这里 5 mm 对 1 mm 直径给边缘留出足够的空白区域避免周期性边界条件引入的伪影。4.2 构造圆孔孔径函数硬边与软边的选择% 构造圆孔孔径 R sqrt(X.^2 Y.^2); U0 double(R a); % 硬边圆孔这一行double(R a)生成的是理想的硬边圆孔孔内为1、孔外为0。硬边在数学上干净但在数值上会带来高频分量因为阶跃函数的频谱衰减很慢。如果你的采样不够密硬边会引入明显的振铃。我在实际项目里有时会用软边圆孔来抑制数值振铃比如用平滑过渡% 软边圆孔可选 edge_width 2*dx; U0 0.5*(1 - tanh((R - a)/edge_width));软边的物理含义是孔径边缘不是理想突变这在真实光学元件里反而更接近实际加工总有过渡区。但要注意软边会改变衍射图样的细节做理论对照时还是应该用硬边。我的建议是验证算法用硬边工程仿真可以试软边看稳健性。4.3 角谱传播的核心计算频域乘传递函数% 频域坐标 fx (-N/2:N/2-1)/(N*dx); [FX, FY] meshgrid(fx, fx); % 传递函数 H exp(1j*k*z*sqrt(1 - (lambda*FX).^2 - (lambda*FY).^2)); H((lambda*FX).^2 (lambda*FY).^2 1) 0; % 倏逝波置零 % 传播 U0_fft fftshift(fft2(ifftshift(U0))); U1_fft U0_fft .* H; U1 fftshift(ifft2(ifftshift(U1_fft))); % 光强 I abs(U1).^2;这段是整个代码的心脏。几个细节必须说清楚。第一fftshift和ifftshift的配合是为了让零频分量居中避免坐标错位。很多人第一次写会漏掉ifftshift结果图样整体平移排查起来很费劲。第二倏逝波置零那一步不能省否则根号内为负会产生复数相位数值上会爆炸。第三传递函数里的sqrt在频域边缘附近变化极快如果采样在频域不够密这里就是混叠的高发区。我实测下来当 $N2048$、$L5$ mm 时频域采样间隔约为 $1/(N\Delta x) \approx 0.2\ \text{mm}^{-1}$对 632.8 nm 波长来说$1/\lambda \approx 1580\ \text{mm}^{-1}$频域范围远大于此传递函数的有效区域被充分覆盖结果稳定。4.4 结果可视化让光强分布会说话figure; imagesc(x*1e3, x*1e3, I); axis square; colormap(hot); colorbar; xlabel(x (mm)); ylabel(y (mm)); title(圆孔菲涅尔衍射光强分布); % 轴上光强曲线 figure; plot(x*1e3, I(N/21, :), b, LineWidth, 1.2); xlabel(x (mm)); ylabel(归一化光强); title(过中心水平截面光强); grid on;可视化不是随便画个图就完事。二维图用imagesc配合axis square能保证圆对称性不被拉伸一维截面图则能定量读出环的位置和对比度。我习惯把光强归一化到最大值这样不同参数下的图样可以直接对比。另外colormap(hot)对观察弱环比较友好因为它的低值区对比度较高。提示如果二维图看起来糊或者环不圆先检查axis square是否加上再检查坐标轴是否用了物理单位。很多时候不是算法问题是显示问题。5. 结果验证怎么判断你算的衍射图是对的5.1 用轴上光强振荡对照菲涅尔半波带理论算完之后最直接的验证是看轴上光强随距离的变化。理论上轴上光强随 $z$ 应该出现明暗交替极大值出现在孔径包含奇数个半波带时。你可以固定孔径扫描一系列 $z$ 值把轴上光强画出来看振荡周期是否符合 $z_n a^2/(n\lambda)$ 的规律。我做过这个扫描用 0.5 mm 半径、632.8 nm 波长理论上前几个极大大约在 $z \approx 0.395$ m、$0.132$ m 等位置。仿真曲线和理论位置的偏差在几个百分点以内主要来自离散采样和硬边近似。如果偏差很大八成是采样或传播距离设置有问题。5.2 远场极限下与艾里斑对照另一个强验证是把传播距离拉大让菲涅尔数远小于 1此时结果应该趋近夫琅禾费衍射的艾里斑。艾里斑第一暗环半径 $r_1 1.22\lambda z/D$。比如 $z10$ m、$D1$ mm、$\lambda632.8$ nm$r_1 \approx 7.7$ mm。你可以在仿真里量第一暗环位置和这个值对比。如果对得上说明你的传播算法在远场极限下是正确的。这个对照特别有价值因为它同时检验了波长、孔径、距离三个量的量纲关系。我遇到过有人把孔径半径和直径搞混结果差了两倍就是用这个方法抓出来的。5.3 能量守恒检查一个容易被忽略的自检角谱传播在无吸收介质中应该保持总能量不变忽略倏逝波损失。你可以在传播前后分别对 $|U|^2$ 求和看比值是否接近 1。如果能量明显不守恒通常是频域处理出了问题比如倏逝波没置零、或者fftshift用错导致频域错位。我一般把能量比作为代码的健康指标每次改参数后顺手看一眼。正常情况应该在 0.99 以上。低于这个值先别急着分析物理先把数值问题解决掉。6. 实操中踩过的坑与参数调优经验6.1 采样窗口太小导致的假环有一次我把孔径面尺寸 $L$ 设成刚好等于孔径直径想着省计算量。结果衍射图外围出现了一圈规则的花纹看起来像多了几级衍射环。排查后发现这是周期性边界条件导致的FFT 隐含假设信号是周期的孔径紧贴边界时相邻周期的孔径会串扰产生虚假干涉。解决办法很简单让 $L$ 至少是孔径直径的 3 到 5 倍给边缘留足空白。代价是同样采样点数下空间分辨率下降所以要么加大 $N$要么接受稍粗的采样。我通常取 $L 5D$ 左右兼顾分辨率和边界安全。6.2 传播距离过小时的频域混叠角谱法在传播距离很小时传递函数的相位变化非常剧烈频域采样稍有不足就会混叠。表现是近场图样出现高频噪点或非物理的条纹。这时候有两个选择一是加大 $N$二是改用菲涅尔卷积法它在近场小距离下反而更稳。我的经验是当 $z$ 小于孔径直径的若干倍时优先考虑卷积法或直接积分法当 $z$ 较大、需要覆盖近场到远场时用角谱法。没有一种方法通吃关键是知道每种方法的舒适区。6.3 硬边圆孔的振铃与平滑处理硬边圆孔的阶跃在数值上会产生吉布斯振铃表现为衍射图边缘的细小波动。这不是物理效应是数值伪影。除了前面提到的软边处理还可以在频域加一个温和的低通滤波但要注意别把真实的衍射环也滤掉。我一般先不加滤波看振铃是否影响主要结论。如果只是边缘细节可以接受如果影响到第一暗环位置就得处理。处理时优先加采样其次才是滤波因为加采样是从根源上解决问题。6.4 参数扫描时的效率优化做参数扫描比如扫距离、扫孔径时如果每次都重新算传递函数和FFT会很慢。我的优化做法是把孔径的FFT预先算好存起来因为孔径不变时它不变传递函数随 $z$ 变但可以向量化批量计算。这样一轮扫描能快好几倍。另外如果只是看轴上光强其实不需要算整个二维场可以用一维的轴上衍射公式近似速度快得多。当然要看完整图样还是得算二维。7. 从圆孔到真实系统这个模型还能怎么扩展圆孔菲涅尔衍射算通之后它的价值远不止于一张漂亮的图样。往小了说它是理解更复杂孔径衍射的跳板往大了说它是把衍射效应纳入光学系统评估的入口。一个自然的扩展是换成环形孔径或带遮挡的圆孔这在望远镜、显微物镜里很常见。代码改动很小只需修改孔径函数。另一个扩展是引入像差比如在孔径面上叠加一个球面相位因子模拟离焦或者叠加泽尼克多项式模拟实际系统的波前误差。这时候衍射计算就从验证理论变成了评估系统性能。再进一步可以把单波长扩展到多波长或宽带观察色差对衍射图样的影响也可以把标量衍射扩展到矢量衍射处理高数值孔径情形。每一步扩展都会带来新的数值挑战但核心方法论——选对传播模型、管好采样、做好验证——是不变的。我个人在实际项目里的体会是圆孔菲涅尔衍射这个小题目其实是训练衍射数值计算全套肌肉记忆的最佳载体。把它从头到尾算准、验证透再遇到矩形孔、相位光栅、甚至三维散射问题心里就有底了。最后分享一个小技巧每次改完参数先跑一个已知解析解的简单情形做回归测试确认代码没被改坏再上复杂参数。这个习惯帮我省下了无数次结果不对却不知道从哪查起的时间。

读完文章,也想定制专属网站?

尧图设计师 24 小时内与您沟通定制方案

免费获取报价 →
↑