EMAN2
Classes | Typedefs | Enumerations | Functions
varimax.h File Reference
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Classes

struct  methodName

Typedefs

typedef struct methodName methodName

Enumerations

enum  rotationScratch { GFNORM = 0, GKNORM, GLABELS, NTRASH }
enum  rotationMethods {
  IVARIMAX = 0, IQUARTIMAX, IEQUIMAX, IORTHOMAX,
  IOBLIMIN, NMETHODS, NOTAVAILABLE = IOBLIMIN
}

Functions

int varmx (float *aload, int nv, int nf, int method, float *params, float *fnorm, int itmax, float eps, int verbose)

Typedef Documentation

typedef struct methodName methodName

Enumeration Type Documentation

Enumerator:
IVARIMAX 
IQUARTIMAX 
IEQUIMAX 
IORTHOMAX 
IOBLIMIN 
NMETHODS 
NOTAVAILABLE 

Definition at line 30 of file varimax.h.

{
        IVARIMAX = 0,
        IQUARTIMAX,
        IEQUIMAX,       
        IORTHOMAX,
        IOBLIMIN,
        NMETHODS,
        NOTAVAILABLE = IOBLIMIN /* first non-implemented recognized method*/
};
Enumerator:
GFNORM 
GKNORM 
GLABELS 
NTRASH 

Definition at line 22 of file varimax.h.


Function Documentation

int varmx ( float *  aload,
int  nv,
int  nf,
int  method,
float *  params,
float *  fnorm,
int  itmax,
float  eps,
int  verbose 
)

Definition at line 120 of file varimax.cpp.

References b, compcrit(), IORTHOMAX, and t.

Referenced by EMAN::varimax::analyze(), and doRotation().

{
        float         crit, startCrit, fnv = (float) nv;
        float        *aloadj, *aloadk;
        float         denominator, numerator, angl, trot;
        float         eps1 = eps, eps2 = eps;
        float         lambda = 0.0;     //avoid use lambda uninitialized
        int           inoim = 0, ict = 0, irot = 0;
        int           i, j, k, iflip, nf1 = nf - 1;

        if (method <= IORTHOMAX)
        {
                lambda = params[0];
        }

        startCrit = crit = compcrit(aload, nv, nf, lambda);

        do /*while (inoim < 2 && ict < itmax && iflip);*/
        {
                float      oldCrit = crit;

                iflip = 0;
                aloadj = aload;

                for (j = 0;j < nf1 ;j++)
                {
                        aloadk = aloadj + nv;
                        for (k = j + 1;k < nf ;k++)
                        {
                                float      a = 0.0, b = 0.0, c = 0.0, d = 0.0, s = 0.0;
                                
                                for (i = 0;i < nv ;i++)
                                {
                                        float    c2 = aloadj[i]*aloadj[i] - aloadk[i]*aloadk[i];
                                        float    s2 = 2.0f*aloadj[i]*aloadk[i];

                                        a += c2;
                                        b += s2;
                                        c += c2*c2 - s2*s2;
                                        d += c2*s2;
                                } /*for (i = 0;i < nv ;i++)*/

                                denominator = fnv*c + lambda*(b*b - a*a);
                                numerator = 2.0f*(fnv*d - lambda*a*b);

                                if (fabs(numerator) > eps1*fabs(denominator))
                                {
                                        iflip = 1;
                                        irot++;
                                        angl = 0.25f*atan2(numerator,denominator);
                                        
                                        c = cos(angl);
                                        s = sin(angl);
                                        for (i = 0;i < nv ;i++)
                                        {
                                                float   t = c*aloadj[i] + s*aloadk[i];

                                                aloadk[i] = -s*aloadj[i] + c*aloadk[i];
                                                aloadj[i] = t;
                                        } /*for (i = 0;i < nv ;i++)*/
                                } /*if (fabs(numerator) >= eps1*fabs(denominator))*/
                                aloadk += nv;
                        } /*for (k = j + 1;k < nf ;k++)*/
                        aloadj += nv;
                } /*for (j = 0;j < nf1 ;j++)*/
                ict++;

                crit = compcrit(aload, nv, nf, lambda);
                trot = (crit > 0.0f) ? (crit - oldCrit)/crit : 0.0f;
                inoim++;
                if (trot > eps2)
                {
                        inoim = 0;
                }
        } while (inoim < 2 && ict < itmax && iflip);

        if (fnorm != (float *) 0)
        {
                aloadj = aload;
                for (j = 0;j < nf ;j++)
                {
                        float     ssj = 0, sj = 0;
                        
                        for (i = 0;i < nv ;i++)
                        {
                                sj += aloadj[i];
                                ssj += aloadj[i]*aloadj[i];
                        } /*for (i = 0;i < nv ;i++)*/
                        fnorm[j] = ssj;
                        if (sj <= 0.0)
                        {
                                for (i = 0;i < nv ;i++)
                                {
                                        aloadj[i] = -aloadj[i];
                                }
                        } /*if (sj <= 0.0)*/

                        aloadk = aload;
                        for (k = 0;k < j ;k++)
                        {
                                if (fnorm[k] < fnorm[j])
                                {
                                        float       t = fnorm[k];

                                        fnorm[k] = fnorm[j];
                                        fnorm[j] = t;
                                        for (i = 0;i < nv ;i++)
                                        {
                                                t = aloadj[i];
                                                aloadj[i] = aloadk[i];
                                                aloadk[i] = t;
                                        } /*for (i = 0;i < nv ;i++)*/
                                } /*if (fnorm[k] < fnorm[j])*/
                                aloadk += nv;
                        } /*for (k = 0;k < j ;k++)*/
                        aloadj += nv;
                } /*for (j = 0;j < nf ;j++)*/
        } /*if (fnorm != (float *) 0)*/

        /*
        if (verbose)
        {
                char   *outstr = OUTSTR;
                
                outstr += formatChar(outstr, Methods[method].name, CHARASIS);
                outstr += formatChar(outstr, " starting criterion = ", CHARASIS);
                outstr += formatDouble(outstr, startCrit, DODEFAULT | TRIMLEFT);
                outstr += formatChar(outstr, ", final criterion = ", CHARASIS);
                outstr += formatDouble(outstr, crit, DODEFAULT | TRIMLEFT);
                putOUTSTR();
                sprintf(OUTSTR, "%ld iterations and %ld rotations", ict, irot);
                putOUTSTR();
        } if (verbose)*/

        return (ict < itmax);
} /*varmx()*/