- android - 多次调用 OnPrimaryClipChangedListener
- android - 无法更新 RecyclerView 中的 TextView 字段
- android.database.CursorIndexOutOfBoundsException : Index 0 requested, 光标大小为 0
- android - 使用 AppCompat 时,我们是否需要明确指定其 UI 组件(Spinner、EditText)颜色
我试图通过在 python 2.7 中使用 scipy.optimize.fsolve
找到方程组的解。目标是计算化学系统的平衡浓度。由于问题的性质,一些常量非常小。现在对于某些组合,我确实得到了适当的解决方案。对于某些参数,我找不到解决方案。要么解是负的,这从物理角度来看是不合理的,要么 fsolve 产生:
ier = 3, 'xtol=0.000000 太小,无法进一步改进\n近似解。')
ier = 4, '迭代没有取得很好的进展,正如最近五次雅可比评估的\n 改进所衡量的那样。')
ier = 5, '迭代没有取得很好的进展,根据最近十次迭代\n 的改进来衡量。')
根据我的研究,在我看来,未能找到方程组的正确解与数据类型 float.64
不够精确有关。正如一位 friend 指出的那样,系统条件不佳,参数相差几个数量级。所以我尝试将 fsolve 与 gmpy2
模块提供的 mpfr
类型一起使用,但这导致了以下错误:
TypeError:无法根据规则“安全”将数组数据从 dtype('O') 转换为 dtype('float64')
现在这里有一个带有参数的小例子,如果随机化的起始参数恰好合适,它会导致一个解决方案。然而,如果常数 C_HCL 被选择为类似 1e-4 或更大的东西,那么我永远找不到合适的解决方案。
from numpy import *
from scipy.optimize import *
K_1 = 1e-8
K_2 = 1e-8
K_W = 1e-30
C_HCL = 1e-11
C_NAOH = K_W/C_HCL
C_HL = 1e-6
if C_HCL-C_NAOH > 0:
Saeure_Base = C_HCL-C_NAOH+sqrt(K_W)
OH_init = K_W/(Saeure_Base)
elif C_HCL-C_NAOH < 0:
OH_init = C_NAOH-C_HCL+sqrt(K_W)
Saeure_Base = K_W/OH_init
# some randomized start parameters
G1 = random.uniform(0, 2)*Saeure_Base
G2 = random.uniform(0, 2)*OH_init
G3 = random.uniform(1, 2)*C_HL*(sqrt(K_W))/(Saeure_Base+OH_init)
G4 = random.uniform(0.1, 1)*(C_HL - G3)/2
G5 = C_HL - G3 - G4
zGuess = array([G1,G2,G3,G4,G5])
#equation system / 5 variables --> H3O, OH, HL, H2L, L
def myFunction(z):
H3O = z[0]
OH = z[1]
HL = z[2]
H2L = z[3]
L = z[4]
F = empty((5))
F[0] = H3O*L/HL - K_1
F[1] = OH*H2L/HL - K_2
F[2] = K_W - OH*H3O
F[3] = C_HL - HL - H2L - L
F[4] = OH+L+C_HCL-H2L-H3O-C_NAOH
return F
z = fsolve(myFunction,zGuess, maxfev=10000, xtol=1e-15, full_output=1,factor=0.1)
print z
所以问题是。这个问题是基于 float.64 的精度和 如果是,(如何)可以用 python 解决? fsolve 是要走的路吗?我是否需要更改 fsolve 函数以使其接受不同的数据类型?
最佳答案
问题的根源要么是理论上的,要么是数值上的。
scipy.optimize.fsolve
函数基于 MINPACK Fortran 求解器 (http://www.netlib.org/minpack/)。该求解器使用 Newton-Raphson 优化算法来提供解决方案。
当您使用此算法时,存在关于函数平滑度的基本假设。例如,解点 x
处的雅可比矩阵应该是可逆的。您更关心的是吸引力盆地。为了收敛,算法的起点需要靠近实际解,即在吸引盆地中。凸函数始终满足此条件,但是很容易找到该算法对某些函数表现不佳的函数。您的函数就是其中之一,因为您只有一小部分输入参数。
要解决此问题,您只需更改起点即可。这个起点对于具有多个解决方案的函数也变得非常重要:this picture来自维基百科的文章向您展示了根据起点找到的解决方案(五种解决方案的五种颜色);所以你应该小心你的解决方案并实际检查你的解决方案的“物理”方面。
对于数值方面,Newton-Raphson 算法需要有雅可比矩阵(导数矩阵)的值。如果未将其提供给 MINPACK 求解器,则使用有限差分公式估计雅可比矩阵。需要提供有限差分公式的扰动步长epsfcn=None
,None
仅在fprime
的情况下作为默认值提供(在这种情况下不需要雅可比估计)。所以首先你应该合并它。您也可以通过手动推导函数来直接指定雅可比矩阵。
但是,步长的最小值将是机器精度,也称为 machine epsilon .对于您的问题,您的输入值非常小,这可能是个问题。我建议将它们中的每个乘以相同的值(如 10^6),这相当于更改单位,但会避免舍入误差和机器精度问题。
当您查看您提供的参数 xtol=1e-15
时,这个问题也很重要。在您的错误消息中,它给出了 xtol=0.000000
,因为它低于机器精度并且不能被考虑在内。此外,如果您查看行 F[2] = K_W - OH*H3O
,考虑到机器精度,K_W
是否为 1e- 并不重要15
或 1e-30
。与机器精度相比,0
是针对这两种情况的解决方案。为避免此问题,只需将所有内容乘以一个更大的值即可。
总结一下:
关于python - 带 fsolve 的方程系统,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/46423069/
在我的一门类(class)中,我接到了一项家庭作业,要求我们在谷歌上搜索 Metapost 语言并找到该语言中方程求解功能的用途。 在浏览了 Metapost 用户手册的前十多页后,我发现只有一个原因
你能帮我在 this page 上的谷歌图表上隐藏趋势线上的工具提示(方程)吗? ? 谢谢 以下是我正在使用的图表选项: var options = { title: 'Weight
我正在尝试将 TeXWorks 编辑器配置为使用与 TeXMaker 相同的语法着色。但是,TexWorks 使用正则表达式来指定应该着色的内容。不幸的是,它没有数学的默认设置。 我想匹配 $ 之间的
我刚开始玩 GHCi。我看到列表生成器基本上解决了给定集合中的方程式: Prelude> [x | x [0.01,0.2..2.0] [1.0e-2,0.2,0.39,0.580000000000
是否有可以使用的图形表达式生成器或方程编辑器的 Java 开源实现? 最好有在线演示,或者至少有屏幕截图。 最佳答案 取决于方程的类型。 如果您正在考虑简单的多项式,您可以尝试 Java Expres
我有四个文本输入字段,在用户输入相关值后,我必须进行 JavaScript 计算以将它们全部相加 我使用: var total = Number(value1) + Number(value2) +
为什么这段代码有两个不同的输出(GCC 4.5.1)(我已经评论了重要的行): int main() { bool a = 1; bool b = 1; bool c = 1;
如果标题含糊不清,我深表歉意,但我不知道如何为我的情况命名。我正在为使用 GPS 的 iPhone 编写一个应用程序。在 didUpdateLocations: 方法中,我针对任意大小的变量测试位置的
我正在尝试计算表中学生的 BMI,四舍五入到三位数: +-------+--------+--------+ | fname | weight | height | +-------+--------
我们可以使用 deSolve R 中的常微分方程 (ODE) 包,但是,我找不到解决两个嵌套 ODE 方程的方法,假设` b'(t) = beta - k*b(t); a'(t) = alpha -b
我有一个 boolean 方程,想简化它。帮忙解决一下。 bool needLoad = isA || (!isA && !isB); 之后我使用 if (needLoad){ if (
我很感兴趣,建模工具(在我的例子中是 OpenModelica 和 Dymola - 建模语言 Modelica)如何求解方程组(线性和/或非线性)。这些工具专为求解微分代数方程而设计。我知道一点将微
Julia:当我有绘图时如何找到最佳拟合曲线/方程?我有一个用 map 绘制的图,但我需要找到一个适合它的二次方程? 最佳答案 正如评论中所说,有一个情节在这里并不真正相关;只有数据本身是。您可以使用
我一直在尝试将像 100, 45 这样的输入放入文本框中,并通过单击按钮通过我的方程式运行它,但我不知道该怎么做。单击按钮后,它应该发布答案作为警报。请帮忙。谢谢。 function Rad(a, b
Julia:当我有绘图时如何找到最佳拟合曲线/方程?我有一个用 map 绘制的图,但我需要找到一个适合它的二次方程? 最佳答案 正如评论中所说,有一个情节在这里并不真正相关;只有数据本身是。您可以使用
有人可以向我解释为什么下面的代码会打印字符“u”吗? int p = 9; int q = 5; int r = p - q; double x = p; double y = q; St
我想以某种方式缩短我的 ODE 方程,因为否则代码会变得困惑。我尝试过使用辅助函数,例如这里的 fe() ,但这不起作用。下面的代码只是一个例子,欢迎任何建议!谢谢! # Import the req
我无法创建正确的文件。程序中的方程不会迭代,它只会根据请求的数量写入相同的总和。 for 循环。 #include #include #include #define LEN 256 int m
我有 2 个指向一些 Point 结构的指针。我想计算两点之间的距离(我不需要计算它的根)所以我有这个: w[0]=X[l]; w[1]=X[l+1]; d=m(w[0]->x
我有一个具有 CSV 上传功能的网站,它将 CSV 中的所有内容推送到临时表,然后分成较小的表。 目前,我有一个显示页面,在 HTML 表格中显示所有这些信息。然而,有些部分需要有公式化的表示。换句话
我是一名优秀的程序员,十分优秀!