Hello,

I had a look at the source in interpr3.cxx and have made the proposed changes for the COVAR function. Although I'm a very beginner I think, that I'm able to change some of the other such functions too.

The changes need to calculate the mean in a first loop and than calculating the other results in a second loop. My question is, whether you want, that the functions are changed in that way. If yes, I would be glad, to do that job.

For COVAR it looks like this (based on OOF680_m18):

--- interpr3original.cxx        2006-07-21 13:34:30.000000000 +0200
+++ interpr3Version1Covar.cxx   2007-07-04 23:00:28.656250000 +0200
@@ -3656,13 +3656,18 @@
                SetIllegalParameter();
                return;
        }
+       //#issue 78250
+       //(sum((X-MeanX)(Y-MeanY)))/N equals (SumXY)/N-MeanX*MeanY 
mathematically,
+       // but the latter produces wrong results if the absolute values are 
high,
+       // for example above 10^7
        double fCount   = 0.0;
        double fSumX    = 0.0;
        double fSumY    = 0.0;
-       double fSumXY   = 0.0;
+       double fSumDeltaXDeltaY   = 0.0; // sum of (ValX-MeanX)*(ValY-MeanY)
        double fValX, fValY;
+       double fMeanX, fMeanY;
        for (SCSIZE i = 0; i < nC1; i++)
-               for (SCSIZE j = 0; j < nR1; j++)
+         for (SCSIZE j = 0; j < nR1; j++)
                {
                        if (!pMat1->IsString(i,j) && !pMat2->IsString(i,j))
                        {
@@ -3670,14 +3675,27 @@
                                fValY = pMat2->GetDouble(i,j);
                                fSumX    += fValX;
                                fSumY    += fValY;
-                               fSumXY   += fValX*fValY;
                                fCount++;
                        }
                }
        if (fCount < 1.0)
                SetNoValue();
        else
-               PushDouble( (fSumXY-fSumX*fSumY/fCount)/fCount);
+  {
+    fMeanX = fSumX/fCount;
+    fMeanY = fSumY/fCount;
+    for (SCSIZE i = 0; i < nC1; i++)
+           for (SCSIZE j = 0; j < nR1; j++)
+           {
+                       if (!pMat1->IsString(i,j) && !pMat2->IsString(i,j))
+                       {
+                                 fValX = pMat1->GetDouble(i,j);
+                                 fValY = pMat2->GetDouble(i,j);
+                                 fSumDeltaXDeltaY 
+=(fValX-fMeanX)*(fValY-fMeanY);
+                         }
+                 }
+               PushDouble( fSumDeltaXDeltaY/fCount);
+       }
 }



kind regards
Regina

---------------------------------------------------------------------
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]

Reply via email to