<p>解决这样问题的“正确方法”是以下一种或多种:</p>
<ol>
<li>找到更有效的配方</li>
<li>象征性地简化和减少术语</li>
<li>使用矢量化(例如NumPy)</li>
<li>将双关键转到已经优化的低级库(例如,在隐式执行强表达式优化的C或Fortran语言中,而不是Python,后者确实<em>nada</em>)。</li>
</ol>
<p>不过,让我们暂时假设,方法1、3和4不可用,您必须使用Python来实现这一点。然后简化和“提升”公共子表达式是您的主要工具。</p>
<p>好消息是,机会有很多。例如,表达式^{cd1>}重复26次。您可以只分配^{{cd2>}一次,然后每次替换^{cd1>}即可节省25个计算。</p>
<p>当您开始在这里查找公共表达式时,您会发现它们在任何地方都</em>。把这个过程机械化会很好的,对吧?通常,这需要一个完整的表达式解析器(例如来自^{cd4>}模块),这是一个指数时间优化问题。但你的表情有点特殊。虽然长而多变,但并不特别复杂。它没有什么内部的假肢分组,所以我们可以用更快更脏的方法来摆脱。</p>
<p>在“如何”之前,结果代码为:</p>
<pre class="lang-py prettyprint-override"><code>sa = r**6 # 26 occurrences
sb = u1**2 # 5 occurrences
sc = u2**2 # 5 occurrences
sd = v1**2 # 5 occurrences
se = u1**4 # 4 occurrences
sf = u2**3 # 3 occurrences
sg = u1**3 # 3 occurrences
sh = v1**4 # 3 occurrences
si = u2**4 # 3 occurrences
sj = v1**3 # 3 occurrences
sk = v2**2 # 1 occurrence
sl = v1**6 # 1 occurrence
sm = v1**5 # 1 occurrence
sn = u1**6 # 1 occurrence
so = u1**5 # 1 occurrence
sp = u2**6 # 1 occurrence
sq = u2**5 # 1 occurrence
sr = 6*sa # 6 occurrences
ss = 3*sa # 5 occurrences
st = ss*t # 5 occurrences
su = 12*sa # 4 occurrences
sv = sa*t # 3 occurrences
sw = v1*v2 # 5 occurrences
sx = sj*v2 # 3 occurrences
sy = 24*sv # 3 occurrences
sz = 15*sv # 2 occurrences
sA = sr*u1 # 2 occurrences
sB = sy*u1 # 2 occurrences
sC = sb*sc # 2 occurrences
sD = st*se # 2 occurrences
# revised formula
sv*sn - sr*so*u2 - sz*se*sc +
20*sa*sg*sf + sz*sb*si - sA*sq -
sv*sp + sD*sd - su*sg*u2*sd -
18*sv*sC*sd + su*u1*sf*sd +
st*si*sd + st*sb*sh - sA*u2*sh -
st*sc*sh + sv*sl - sr*se*sw -
sy*sg*u2*sw + 36*sa*sC*sw +
sB*sf*sw - sr*si*sw -
su*sb*sx - sB*u2*sx +
su*sc*sx - sr*sm*v2 - sD*sk
</code></pre>
<p>这样就避免了81次计算。只是个粗略的伤口。甚至可以进一步改善结果。例如,可以预先计算子表达式^{cd5}和^{cd6>}。但我们会把下一层留一天。</p>
<p>注意,这不包括起始^{cd7>}。大多数简化可以(而且需要)在表达的核心上进行,而不是从外部术语上。所以我现在把它们去掉了,一旦计算出公共核心,它们就可以被添加回去。</p>
<p>你怎么做到的?</p>
^{pr2}$
<p>使用正则表达式解析是一项棘手的工作。那次旅行容易出错、悲伤和遗憾。我通过提升一些不需要严格的指数来防止不良结果,并将随机值插入公式的前后,以确保它们都给出相同的结果。如果这是生产代码,我建议使用“双关到C”策略。但如果你不能。。。</p>