PDL::Minuit中mn_def_pars()函数参数初始化异常问题求助
PDL::Minuit mn_def_pars重复使用向量首个元素问题
你的操作完全正确,这是PDL::Minuit模块底层实现的bug,和你的代码写法无关。
问题根源
PDL::Minuit的mn_def_pars函数在处理PDL类型的参数初始值和步长时,XS绑定代码没有正确遍历整个PDL数组,而是把第一个元素的内存地址重复传递给了底层的Minuit库接口,导致所有参数都被设置成了第一个元素的值。
查看模块的XS实现代码(比如Minuit.xs)会发现,在循环定义参数时,程序没有正确索引PDL数组的每个元素,而是始终引用第一个元素的位置。例如,可能存在类似这样的错误代码:
double *par_vals = (double*) $pars->get_dataref(); double *step_vals = (double*) $steps->get_dataref(); for (int i=0; i<npars; i++) { // 错误:始终用par_vals[0]而非par_vals[i] mnparm(i+1, names[i], par_vals[0], step_vals[0], 0, 0); }
解决方案(非临时方法)
- 修复模块XS代码:修改
mn_def_pars的XS实现,在循环中正确索引PDL数组的每个元素,将par_vals[i]和step_vals[i]传递给mnparm函数。 - 提交bug报告:向PDL::Minuit的维护者提交该问题,附带你的测试代码和现象,推动官方修复。
- 绕过mn_def_pars直接调用底层函数:如果需要立即使用,可以在Perl代码中逐个定义参数,避免使用有问题的
mn_def_pars:
use PDL::LiteF; use PDL::Minuit; mn_init(\&$chi2, {Title => 'test title'}); # 逐个定义参数 mnparm(1, 'intercept', 2.5, 0.3, 0, 0); mnparm(2, 'slope', 3.0, 0.5, 0, 0);
内容的提问来源于stack exchange,提问作者Enredanrestos
相关产品推荐
相关产品推荐

