manim边做边学--隐函数图像
<p>在数学可视化中,<strong>显函数</strong>$ y=f(x) $相对容易处理,但 <strong>隐函数</strong> $ F(x,y)=0 $ 的绘制则更具挑战性。</p><p><code>Manim</code>库中的<code>ImplicitFunction</code>类专门用于解决这个问题,它能够高效地绘制各种复杂的隐函数曲线。</p>
<p><code>ImplicitFunction</code>的<strong>典型应用场景</strong>包括:</p>
<ul>
<li><strong>高等数学教学</strong>:绘制圆锥曲线(椭圆、双曲线)、心形线、双纽线等</li>
<li><strong>工程应用</strong>:可视化等值线、等高线、势能面</li>
<li><strong>物理模拟</strong>:绘制电场/磁场的等势线、相平面轨迹</li>
<li><strong>计算机图形学</strong>:生成特殊曲线和曲面</li>
<li><strong>代数几何</strong>:研究代数曲线的性质</li>
</ul>
<p>今天,我们将深入探讨<code>Manim</code>中的<code>ImplicitFunction</code>类,了解其作用、应用场景以及如何通过实际示例展示其强大功能。</p>
<h1 id="1-主要参数">1. 主要参数</h1>
<p><code>ImplicitFunction</code>的主要参数有:</p>
<table>
<thead>
<tr>
<th>参数</th>
<th>类型</th>
<th>说明</th>
</tr>
</thead>
<tbody>
<tr>
<td><code>func</code></td>
<td>Callable[, float]</td>
<td>必需参数,二元函数F(x,y)</td>
</tr>
<tr>
<td><code>x_range</code></td>
<td>Sequence</td>
<td>x轴的取值范围,如[-3,3]</td>
</tr>
<tr>
<td><code>y_range</code></td>
<td>Sequence</td>
<td>y轴的取值范围,如[-3,3]</td>
</tr>
<tr>
<td><code>color</code></td>
<td>Color</td>
<td>曲线颜色,默认为WHITE</td>
</tr>
<tr>
<td><code>min_distance</code></td>
<td>float</td>
<td>点之间的最小距离(控制曲线精度)</td>
</tr>
<tr>
<td><code>max_quads</code></td>
<td>int</td>
<td>用于渲染的最大四边形数量(性能优化)</td>
</tr>
<tr>
<td><code>use_smoothing</code></td>
<td>bool</td>
<td>是否使用平滑处理(默认True)</td>
</tr>
<tr>
<td><code>delta</code></td>
<td>float</td>
<td>采样步长(影响曲线精度)</td>
</tr>
</tbody>
</table>
<p><code>func</code>参数是隐式函数的形式,这个函数需要接受两个浮点数$ x <span class="math inline">\(和\)</span> y $,并返回一个浮点数。</p>
<h1 id="2-主要方法">2. 主要方法</h1>
<p><code>ImplicitFunction</code>的主要方法有:</p>
<table>
<thead>
<tr>
<th><strong>名称</strong></th>
<th><strong>说明</strong></th>
</tr>
</thead>
<tbody>
<tr>
<td>generate_points</td>
<td>初始化<code>points</code>属性,从而定义形状。这个方法在对象创建时被调用</td>
</tr>
<tr>
<td>init_points</td>
<td>与<code>generate_points</code>类似,用于初始化<code>points</code>属性</td>
</tr>
</tbody>
</table>
<h1 id="3-使用示例">3. 使用示例</h1>
<p>为了更好地理解<code>ImplicitFunction</code>的功能,我们将通过几个示例来展示其在不同场景中的应用。</p>
<h2 id="31-基本隐函数圆">3.1. 基本隐函数(圆)</h2>
<p>这个示例展示最基本的隐函数绘制,通过方程$ x^2+ y^2 = 1 $绘制单位圆。</p>
<p><strong>注意</strong><code>x_range</code>和<code>y_range</code>的设置需要包含整个曲线。</p>
<pre><code class="language-python"># 创建隐函数图像(单位圆)
circle = ImplicitFunction(
lambda x, y: x**2 + y**2 - 1,
color=RED,
x_range=[-1.5, 1.5],
y_range=[-1.5, 1.5],
)
# 添加标签
label = MathTex("x^2 + y^2 = 1").next_to(circle, DOWN)
# 动画展示
self.play(Create(circle), Write(label))
</code></pre>
<p><img src="https://img2024.cnblogs.com/blog/83005/202506/83005-20250602165301381-2083392636.gif" alt="" loading="lazy"></p>
<h2 id="32-动态参数变化椭圆">3.2. 动态参数变化(椭圆)</h2>
<p>这个示例使用<code>ValueTracker</code>和<code>always_redraw</code>实现动态变化的椭圆,展示如何通过改变参数实时更新隐函数图像。</p>
<pre><code class="language-python"># 创建参数跟踪器
a = ValueTracker(1)
b = ValueTracker(1)
# 创建动态椭圆
ellipse = always_redraw(
lambda: ImplicitFunction(
lambda x, y: (x**2) / (a.get_value() ** 2)
+ (y**2) / (b.get_value() ** 2)
- 1,
color=GREEN,
x_range=[-4, 4],
y_range=[-3, 3],
)
)
# 添加参数标签
param_label = always_redraw(
lambda: MathTex(
f"\\frac{{x^2}}{{{a.get_value()**2:.1f}}} + \\frac{{y^2}}{{{b.get_value()**2:.1f}}} = 1",
color=RED,
)
.shift(DOWN * 1.5 + RIGHT * 1.8)
.scale(0.6)
)
self.add(ellipse, param_label)
self.play(a.animate.set_value(2), b.animate.set_value(1.5), run_time=3)
self.play(a.animate.set_value(3), b.animate.set_value(1), run_time=3)
</code></pre>
<p><img src="https://img2024.cnblogs.com/blog/83005/202506/83005-20250602165301442-86253584.gif" alt="" loading="lazy"></p>
<h2 id="33-复杂曲线笛卡尔心形线">3.3. 复杂曲线(笛卡尔心形线)</h2>
<p>这个示例展示复杂隐函数的绘制,绘制了一个心形曲线。</p>
<pre><code class="language-python"> # 创建心形线
heart = ImplicitFunction(
lambda x, y: (x**2 + y**2 - 1) ** 3 - x**2 * y**3,
color=PINK,
x_range=[-1.5, 1.5],
y_range=[-1.2, 1.8],
)
# 添加标签
label = (
MathTex("(x^2 + y^2 - 1)^3 = x^2 y^3", color=GREEN)
.shift(DOWN + RIGHT * 1.8)
.scale(0.6)
)
self.play(Create(heart), Write(label))
</code></pre>
<p><img src="https://img2024.cnblogs.com/blog/83005/202506/83005-20250602165301382-1231273658.gif" alt="" loading="lazy"></p>
<h1 id="4-附件">4. 附件</h1>
<p>文中的代码只是关键部分的截取,完整的代码共享在网盘中(<code>implicit_function.py</code>),</p>
<p>下载地址: 完整代码 (访问密码: 6872)</p><br><br>
来源:https://www.cnblogs.com/wang_yb/p/18907370
頁:
[1]