Algorithm 尽快评估多变量回归关系

Algorithm 尽快评估多变量回归关系,algorithm,performance,math,recurrence,Algorithm,Performance,Math,Recurrence,我有一些函数,它们被赋予了一些变量x,y,z,等等,并在这些点用一些常数系数计算它们各自的多项式,返回值。然后将我的变量设置为这些值,并重复该过程。在psuedo代码中: repeat N times: x_new = f1(x, y, z) y_new = f2(x, y, z) z_new = f3(x, y, z) x = x_new y = y_new z = z_new 函数是这样的 f1(x, y, z) return c0

我有一些函数,它们被赋予了一些变量
x
y
z
,等等,并在这些点用一些常数系数计算它们各自的多项式,返回值。然后将我的变量设置为这些值,并重复该过程。在psuedo代码中:

repeat N times:
    x_new = f1(x, y, z)
    y_new = f2(x, y, z)
    z_new = f3(x, y, z)
    x = x_new
    y = y_new
    z = z_new
函数是这样的

f1(x, y, z)
    return c0 + c1*x + c2*y + c3*z + c4*x*x + c5*x*y + c6*x*z ...
每次我保存变量的中间值,然后绘制结果图。为了有足够的点来制作足够质量的图形,我需要大约1000万个数据点。我有一些代码可以很快地处理3个变量和3次多项式,但是我想扩展它来支持任意数量的变量和任意次数的多项式。这就是事情进展缓慢的地方,我想我需要一种不同的方法

我最初的(硬编码的)c计算器看起来像:

double evaluateTestEP(双x、双y、双z、双*系数){
双和;
总和=系数[0];
总和+=系数[1]*x;
总和+=系数[2]*y;
总和+=系数[3]*z;
总和+=系数[4]*x*y;
总和+=系数[5]*x*z;
总和+=系数[6]*y*z;
总和+=系数[7]*x*x;
总和+=系数[8]*y*y;
总和+=系数[9]*z*z;
总和+=系数[10]*x*y*z;
总和+=系数[11]*x*x*y;
总和+=系数[12]*x*x*z;
总和+=系数[13]*y*y*x;
总和+=系数[14]*y*y*z;
总和+=系数[15]*z*z*x;
总和+=系数[16]*z*z*y;
总和+=系数[17]*x*x*x;
总和+=系数[18]*y*y*y;
总和+=系数[19]*z*z*z;
回报金额;
}
通用代码:

double recursiveEval(双因子,双*位置,整数ndim,双**系数,整数顺序){
如果(!订单)
返回系数**((*系数)++);
双和=0;
对于(int i=0;i
当然,我确信这已经破坏了我的编译器(gcc)进行公共子表达式消除和其他类似优化的能力。我想知道有没有更好的办法。有一点信息我还没能利用——所有的系数都是在程序开始时从25个(重复)的池中提取的。这些span
[-1.2,1.2]
包括在内,如果这有任何区别的话

我考虑过计算多项式的单个项,然后通过简单的
variableA/variableB
乘法将其转换为其他项,但引入的错误量可能有点太多。我还考虑过计算所有小于等于度数
n
的术语,并使用这些术语通过
2n
度数术语构造
n+1
。我不确定如何实现的另一个选择是,利用许多项共享相同系数的事实(pidginhole原则),将这些项考虑在内,这样就有可能将其减少到比扩展表达式中的项更少的所需乘法和加法。但我不知道如何进行这项工作,因为它必须在运行时进行,这将涉及表达式的JIT编译或其他方面

目前,3级的3个变量(总共20个术语)几乎需要6秒,3级的4个变量(总共35个术语)需要13秒多一点。这些将不能很好地扩展到更大的度或更多的变量中(不同项的数量公式是
nck(度+变量,度)
其中
nck
是“n选择k”)。我正在寻找一种改进广义代码性能的方法,理想情况下是渐进的(我怀疑是通过部分因子分解)。我真的不在乎语言;我是用C语言写这段代码的,但是如果你喜欢用其他语言给出一个算法,这对我来说不会是一个问题