IPP Software Navigation Tools IPP Links Communication Pan-STARRS Links

Changeset 23882


Ignore:
Timestamp:
Apr 16, 2009, 11:25:41 AM (17 years ago)
Author:
Paul Price
Message:

Adding function to calculate covariance pseudo-matrix when binning.

Location:
trunk/psLib/src/imageops
Files:
2 edited

Legend:

Unmodified
Added
Removed
  • trunk/psLib/src/imageops/psImageCovariance.c

    r23401 r23882  
    130130}
    131131
     132psKernel *psImageCovarianceBin(int bin, const psKernel *covariance, bool average)
     133{
     134    psKernel *covar;                    // Covariance matrix to use
     135    if (covariance) {
     136        covar = psMemIncrRefCounter((psKernel*)covariance); // Casting away const
     137    } else {
     138        covar = psImageCovarianceNone();
     139    }
     140
     141    // Check for non-finite elements
     142    for (int y = covar->yMin; y <= covar->yMax; y++) {
     143        for (int x = covar->xMin; x <= covar->xMax; x++) {
     144            if (!isfinite(covar->kernel[y][x])) {
     145                psError(PS_ERR_BAD_PARAMETER_VALUE, true,
     146                        "Non-finite covariance matrix element in covariance matrix at %d,%d", x, y);
     147                psFree(covar);
     148                return NULL;
     149            }
     150        }
     151    }
     152
     153    // The following calculation is the same as for psImageCovarianceCalculate(), except that the "convolution
     154    // kernel" has a constant value, and the output covariance kernel is binned down, so we unbin it in the
     155    // ranges for the inputs.
     156
     157    // Values for "convolution kernel"
     158    int binMin = -(bin - 1) / 2, binMax = bin / 2; // Range of "kernel"
     159    int binDiff = binMax - binMin;      // Difference between the max and min
     160    float binVal = average ? 1.0 / PS_SQR(bin) : 1.0; // Value of "kernel" pixels
     161
     162    // Size of the output covariance matrix
     163    int xMin = (covar->xMin - binDiff) / bin + 0.5, xMax = (covar->xMax + binDiff) / bin + 0.5;
     164    int yMin = (covar->yMin - binDiff) / bin + 0.5, yMax = (covar->yMax + binDiff) / bin + 0.5;
     165    psKernel *out = psKernelAlloc(xMin, xMax, yMin, yMax); // Covariance matrix for output
     166
     167    double total = 0.0;                 // Total covariance
     168    for (int y = yMin; y <= yMax; y++) {
     169        // Range for v
     170        int vMin = PS_MAX(binMin + covar->yMin, bin * y + binMin);
     171        int vMax = PS_MIN(binMax + covar->yMax, bin * y + binMax);
     172        for (int x = xMin; x <= xMax; x++) {
     173            // Range for u
     174            int uMin = PS_MAX(binMin + covar->xMin, bin * x + binMin);
     175            int uMax = PS_MIN(binMax + covar->xMax, bin * x + binMax);
     176
     177            double sum = 0.0;           // Sum for value of covariance matrix at (x,y)
     178            for (int v = vMin; v <= vMax; v++) {
     179                // Range for q
     180                int qMin = PS_MAX(v + covar->yMin, binMin);
     181                int qMax = PS_MIN(v + covar->yMax, binMax);
     182                for (int u = uMin; u <= uMax; u++) {
     183                    // Range for p
     184                    int pMin = PS_MAX(u + covar->xMin, binMin);
     185                    int pMax = PS_MIN(u + covar->xMax, binMax);
     186
     187                    double xyuvValue = binVal; // Value for (x,y) --> (u,v)
     188
     189                    double uvpqValue = 0.0; // Value for (u,v) --> (p,q) --> (0,0)
     190                    for (int q = qMin; q <= qMax; q++) {
     191                        for (int p = pMin; p <= pMax; p++) {
     192                            uvpqValue += (double)covar->kernel[q-v][p-u] * (double)binVal;
     193                        }
     194                    }
     195                    sum += xyuvValue * uvpqValue;
     196                }
     197            }
     198            out->kernel[y][x] = sum;
     199            total += sum;
     200        }
     201    }
     202    psTrace("psLib.imageops", 3, "Total covariance: %lf ; Central variance: %f\n", total, out->kernel[0][0]);
     203
     204    psFree(covar);
     205
     206    return out;
     207}
     208
    132209float psImageCovarianceFactor(const psKernel *covariance)
    133210{
  • trunk/psLib/src/imageops/psImageCovariance.h

    r21466 r23882  
    3535    );
    3636
     37/// Calculate the covariance pseudo-matrix for binning
     38psKernel *psImageCovarianceBin(
     39    int bin,                            ///< Binning factor
     40    const psKernel *covariance,         ///< Current covariance pseudo-matrix
     41    bool average                        ///< Averaging pixels when binning?
     42    );
     43
    3744/// Return the pixel-to-pixel covariance factor
    3845float psImageCovarianceFactor(
Note: See TracChangeset for help on using the changeset viewer.