util_sparx.h

Go to the documentation of this file.
00001 
00005 /*
00006  * Author: Pawel A.Penczek, 09/09/2006 (Pawel.A.Penczek@uth.tmc.edu)
00007  * Copyright (c) 2000-2006 The University of Texas - Houston Medical School
00008  *
00009  * This software is issued under a joint BSD/GNU license. You may use the
00010  * source code in this file under either license. However, note that the
00011  * complete EMAN2 and SPARX software packages have some GPL dependencies,
00012  * so you are responsible for compliance with the licenses of these packages
00013  * if you opt to use BSD licensing. The warranty disclaimer below holds
00014  * in either instance.
00015  *
00016  * This complete copyright notice must be included in any revised version of the
00017  * source code. Additional authorship citations may be added, but existing
00018  * author citations must be preserved.
00019  *
00020  * This program is free software; you can redistribute it and/or modify
00021  * it under the terms of the GNU General Public License as published by
00022  * the Free Software Foundation; either version 2 of the License, or
00023  * (at your option) any later version.
00024  *
00025  * This program is distributed in the hope that it will be useful,
00026  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00027  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
00028  * GNU General Public License for more details.
00029  *
00030  * You should have received a copy of the GNU General Public License
00031  * along with this program; if not, write to the Free Software
00032  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
00033  *
00034  */
00035 
00040 #ifndef util__sparx_h__
00041 #define util__sparx_h__
00042 
00043 public:
00044 
00045 static int coveig(int n, float *covmat, float *eigval, float *eigvec);
00046 
00047 static Dict coveig_for_py(int ncov, const vector<float>& covmatpy);
00048 
00049 static Dict ExpMinus4YSqr(float ymax,int nsamples);
00050 
00051 static void WTM(EMData* PROJ, vector<float> SS,int DIAMETER,int NUMP);
00052 
00053 static void WTF(EMData* PROJ,vector<float> SS,float SNR,int K,vector<float> exptable);
00054 
00055 static Dict CANG(float PHI, float THETA, float PSI);
00056 
00057 static void BPCQ(EMData* B, EMData *CUBE,vector<float> DM);
00058 
00059 static vector<float> infomask(EMData* Vol, EMData* mask, bool);
00060 
00061 static void colreverse(float* beg, float* end, int nx);
00062 
00063 static void slicereverse(float* beg, float* end, int nx,int ny);
00064 
00065 static void cyclicshift(EMData* image, Dict params);
00066 
00067 static Dict im_diff(EMData* V1, EMData* V2, EMData* mask=0);
00068 
00081 static EMData* TwoDTestFunc(int Size, float p, float q,  float a, float b,
00082                    int flag=0, float alphaDeg=0); //PRB
00083 
00084 
00096 static void spline_mat(float *x, float *y, int n,  float *xq, float *yq, int m); //PRB
00097 
00110 static void spline(float *x, float *y, int n, float yp1, float ypn, float *y2);
00111   // PRB
00123 static void splint( float *xa, float *ya, float *y2a, int n,
00124                                      float *xq, float *yq, int m);
00125 
00126 
00137 static void Radialize(int *PermMatTr,  float * kValsSorted,
00138             float *weightofkvalsSorted, int Size, int *SizeReturned);
00139 
00140 
00141 
00142 class sincBlackman
00143 {
00144         protected:
00145                 int M; 
00146                 float fc; 
00147                 int ntable;
00148                 vector<float> sBtable;
00149                 virtual void build_sBtable(); 
00150                 float fltb;
00151         public:
00152                 sincBlackman(int M_, float fc_, int ntable_ = 1999);
00153                 virtual ~sincBlackman() {};
00154 
00155                 inline  float sBwin_tab(float x) const {
00156                         float xt;
00157                         if(x<0.0f) xt = -x*fltb+0.5f; else xt = x*fltb+0.5f;
00158                         return sBtable[ (int) xt];
00159                 }
00161                 int get_sB_size() const { return M; }
00162 };
00163 
00164 
00165 
00189 class KaiserBessel
00190 {
00191         protected:
00192                 float alpha, v, r; 
00193                 int N; 
00194                 int K; 
00195                 float vtable; 
00196                 int ntable;
00197                 vector<float> i0table;
00198                 float dtable; 
00199                 float alphar; 
00200                 float fac; 
00201                 float vadjust;
00202                 float facadj; 
00203                 virtual void build_I0table(); 
00204                 float fltb;
00205         public:
00206                 KaiserBessel(float alpha_, int K, float r_,
00207                                      float v_, int N_, float vtable_=0.f,
00208                                          int ntable_ = 5999);
00209                 virtual ~KaiserBessel() {};
00211                 float I0table_maxerror();
00212                 vector<float> dump_table() {
00213                         return i0table;
00214                 }
00216                 virtual float sinhwin(float x) const;
00218                 virtual float i0win(float x) const;
00220                 inline float i0win_tab(float x) const {
00221                 /*float absx = fabs(x);
00222                         int loc = int(round(absx*fltb));
00223                         return i0table[loc];*/
00224                         float xt;
00225                         if(x<0.f) xt = -x*fltb+0.5f; else xt = x*fltb+0.5f;
00226                         return i0table[ (int) xt];
00227                         /*return i0table[ (int) (fabs(x)*fltb+0.5f)];
00228                                 if (absx > vtable) return 0.f;
00229                                 float loc = absx/dtable;
00230                                 return i0table[int(loc + 0.5f)]; */
00231                 }
00233                 int get_window_size() const { return K; }
00235                 class kbsinh_win {
00236                         KaiserBessel& kb;
00237                         public:
00238                         kbsinh_win(KaiserBessel& kb_) : kb(kb_) {}
00239                         float operator()(float x) const {
00240                                 return kb.sinhwin(x);
00241                         }
00242                         int get_window_size() const {return kb.get_window_size();}
00243                 };
00245                 kbsinh_win get_kbsinh_win() {
00246                         return kbsinh_win(*this);
00247                 }
00249                 class kbi0_win {
00250                         KaiserBessel& kb;
00251                         public:
00252                         kbi0_win(KaiserBessel& kb_) : kb(kb_) {}
00253                         float operator()(float x) const {
00254                                 return kb.i0win(x);
00255                         }
00256                         int get_window_size() const {return kb.get_window_size();}
00257                 };
00259                 kbi0_win get_kbi0_win() {
00260                         return kbi0_win(*this);
00261                 }
00262 };
00263 
00264 class FakeKaiserBessel : public KaiserBessel {
00265         public:
00266                 FakeKaiserBessel(float alpha, int K, float r_,
00267                                          float v_, int N_, float vtable_=0.f,
00268                                                  int ntable_ = 5999)
00269         : KaiserBessel(alpha, K, r_, v_, N_, vtable_, ntable_) {
00270                         build_I0table();
00271                 }
00272                 float sinhwin(float x) const;
00273                 float i0win(float x) const;
00274                 void build_I0table();
00275 };
00276 
00288                 static vector<float>
00289                 even_angles(float delta, float t1=0, float t2=90, float p1=0, float p2=359.999);
00290 
00291 
00344                 static float quadri(float x, float y, int nx, int ny, float* image);
00345 
00400                 static float quadri_background(float x, float y, int nx, int ny, float* image, int xnew, int ynew);
00401 
00402                 static float get_pixel_conv_new(int nx, int ny, int nz, float delx, float dely, float delz, float* data, Util::KaiserBessel& kb);
00403 
00404         static float get_pixel_conv_new_background(int nx, int ny, int nz, float delx, float dely, float delz, float* data, Util::KaiserBessel& kb, int xnew, int ynew);
00405 
00406                 static std::complex<float> extractpoint2(int nx, int ny, float nuxnew, float nuynew, EMData *fimage, Util::KaiserBessel& kb);
00407 
00408                 /*static float quadris(float x, float y, int nx, int ny, float* image);*/
00409                 static float bilinear(float xold, float yold, int nsam, int nrow, float* xim);
00410 
00411 
00420                 static float triquad(float r, float s, float t, float* fdata);
00421 
00429                 class Gaussian {
00430                         float sigma;
00431                         float rttwopisigma;
00432                         float twosigma2;
00433                         public:
00434                         Gaussian(float sigma_ = 1.0) : sigma(sigma_) {
00435                                 rttwopisigma = sqrtf(static_cast<float>(twopi)*sigma);
00436                                 twosigma2 = 2*sigma*sigma;
00437                         }
00438                         inline float operator()(float x) const {
00439                                 return exp(-x*x/(twosigma2))/rttwopisigma;
00440                         }
00441                 };
00442         /*static void alrq(float *xim,  int nsam , int nrow , int *numr,
00443                              float *circ, int lcirc, int nring, char mode);*/
00444         static EMData* Polar2D(EMData* image, vector<int> numr, string mode);
00445         static EMData* Polar2Dm(EMData* image, float cns2, float cnr2, vector<int> numr, string cmode);
00446         /*static void alrq_ms(float *xim, int    nsam, int  nrow, float cns2, float cnr2,
00447                             int  *numr, float *circ, int lcirc, int  nring, char  mode);*/
00448         static void alrl_ms(float *xim, int    nsam, int  nrow, float cns2, float cnr2,
00449                             int  *numr, float *circ, int lcirc, int  nring, char  mode);
00450         /*static void alrq_msi(EMData* image,float cns2, float cnr2,
00451                            int  *numr, float *circ, int lcirc, int  nring, char  mode, Util::KaiserBessel&
00452                                                kb);*/
00453         static EMData* Polar2Dmi(EMData* image, float cns2, float cnr2, vector<int> numr, string cmode, Util::KaiserBessel& kb);
00454 
00455         static void  fftr_q(float  *xcmplx, int nv);
00456         static void  fftr_d(double *xcmplx, int nv);
00457         static void  fftc_q(float  *br, float  *bi, int ln, int ks);
00458         static void  fftc_d(double *br, double *bi, int ln, int ks);
00459         static void  Frngs(EMData* circ, vector<int> numr);
00460         static void  Normalize_ring(EMData* ring, const vector<int>& numr);
00461         static void  Frngs_inv(EMData* circ, vector<int> numr);
00462 
00463         /*
00464                 A little notes about different Crosrng:
00465                 Basically, they all do cross-correlation function to two images in polar coordinates
00466                 Crosrng_e is the original one
00467                 Crosrng_ew is the one that you could apply weights to different rings
00468                 Crosrng_ms assumes the user already apply weights to circ1, it also returns both
00469                            straight and mirrored positions simultaneously.
00470                 Crosrng_msg differs from the previous ones in that it returns the cross-correlation
00471                             function entirely instead of the peak value and position, thus makes it
00472                             possible to use the gridding method to determine the peak position
00473                 Crosrng_msg_s is same as Crosrng_msg except that it only checks straight position
00474                 Crosrng_msg_m is same as Crosrng_msg except that it only checks mirrored position
00475           */
00476         static Dict Crosrng_e(EMData* circ1, EMData* circ2, vector<int> numr, int neg);
00477         static Dict Crosrng_ew(EMData* circ1, EMData* circ2, vector<int> numr, vector<float> w, int neg);
00478 
00479         static Dict Crosrng_ms(EMData* circ1, EMData* circ2, vector<int> numr);
00480         static Dict Crosrng_sm_psi(EMData* circ1, EMData* circ2, vector<int> numr, float psi, int flag);
00481         static Dict Crosrng_ns(EMData* circ1, EMData* circ2, vector<int> numr);
00482 
00483         static EMData* Crosrng_msg(EMData* circ1, EMData* circ2, vector<int> numr);
00484         static void Crosrng_msg_vec(EMData* circ1, EMData* circ2, vector<int> numr, float *q, float *t);
00485         static EMData* Crosrng_msg_s(EMData* circ1, EMData* circ2, vector<int> numr);
00486         static EMData* Crosrng_msg_m(EMData* circ1, EMData* circ2, vector<int> numr);
00487 
00488         static vector<float> Crosrng_msg_vec_p(EMData* circ1, EMData* circ2, vector<int> numr );
00489         static void  prb1d(double *b, int npoint, float *pos);
00490 
00491         static void update_fav(EMData* ave,EMData* dat, float tot, int mirror, vector<int> numr);
00492         static void sub_fav(EMData* ave,EMData* dat, float tot, int mirror, vector<int> numr);
00493 
00494         static float ener(EMData* ave, vector<int> numr);
00495 
00496         static float ener_tot(const vector<EMData*>& data, vector<int> numr, vector<float> tot);
00497 
00498         // k-means helper
00499         static Dict min_dist_real(EMData* image, const vector<EMData*>& data);
00500         static Dict min_dist_four(EMData* image, const vector<EMData*>& data);
00501         static int k_means_cont_table_(int* grp1, int* grp2, int* stb, long int s1, long int s2, int flag);
00502 
00503         // new code common-lines
00504         static vector<double> cml_weights(const vector<float>& cml);
00505         static vector<int> cml_line_insino(vector<float> Rot, int i_prj, int n_prj);
00506         static vector<int> cml_line_insino_all(vector<float> Rot, vector<int> seq, int n_prj, int n_lines);
00507         static vector<double> cml_init_rot(vector<float> Ori);
00508         static vector<float> cml_update_rot(vector<float> Rot, int iprj, float nph, float th, float nps);
00509         static vector<double> cml_line_in3d(vector<float> Ori, vector<int> seq, int nprj, int nlines);
00510         static vector<double> cml_spin_psi(const vector<EMData*>& data, vector<int> com, vector<float> weights, int iprj, vector<int> iw, int n_psi, int d_psi, int n_prj);
00511         static double cml_disc(const vector<EMData*>& data, vector<int> com, vector<int> seq, vector<float> weights, int n_lines);
00512         static void set_line(EMData* img, int posline, EMData* line, int offset, int length);
00513         static void cml_prepare_line(EMData* sino, EMData* line, int ilf, int ihf, int pos_line, int nblines);
00514         /* Decimates the image with respect to the image center.
00515          * (i.e) the center of the original image is kept the same
00516          * and then the initial start pixel is calculated with respect to the
00517          * center of the image
00518          * @params(image, x-pixel, y-pixel,z-pixel)
00519          * works for all 3 dimensions
00520         **/
00521         static EMData* decimate(EMData* img, int x_step,int y_step=1,int z_step=1);
00522 
00523         static EMData* window(EMData* img,int new_nx ,int new_ny=1, int new_nz=1, int x_offset=0, int y_offset=0, int z_offset=0);
00524 
00525         static EMData* pad(EMData* img, int new_nx, int new_ny=1, int new_nz=1, int x_offset=0, int y_offset=0, int z_offset=0, char *params="average");
00526 
00527         static vector<float> histogram(EMData* image, EMData* mask, int nbins = 128, float hmin =0.0f, float hmax = 0.0f );
00528 
00529         static Dict histc(EMData *ref,EMData *img,EMData *mask);
00530 
00531         static float hist_comp_freq(float PA,float PB,int size_img, int hist_len, EMData *img, vector<float> ref_freq_hist, EMData *mask, float ref_h_diff, float ref_h_min);
00532 
00533 
00534         /* The unit in the ctf function: dz: Angstrom, cs: CM  Ps: Angstrom, Voltage: Kv,dza: Angstrom, azz: degree wgh: None unit. b_factor: Angstrom^2
00535          The CTF function takes form of   *sin(-quadpi*(dz*lambda*ak^2-cs*lambda^3*ak^4/2.)-wgh)*exp(-b_factor*ak^2)*sign
00536           * sign can be set as +1 or -1 . The unit of frequency ak is 1/Angstrom
00537                   Attention: Envelope function in power spectrum has a form of exp(-b_factor*ak^2)
00538                                           */
00539         static float   tf(float dzz, float ak, float voltage = 300.0f, float cs = 2.0f, float wgh = 0.1f, float b_factor = 0.0f, float sign = -1.0f);
00540         static EMData *compress_image_mask(EMData* image, EMData* mask);
00541         static EMData *reconstitute_image_mask(EMData *image,EMData *mask);
00542         static vector<float> merge_peaks(vector<float> peak1, vector<float> peak2,float p_size);
00543         static vector<float> pw_extract(vector<float>pw, int n, int iswi,float ps);
00544         static vector<float> call_cl1(long int *k,long int *n, float *ps, long int *iswi, float *pw, float *q2, double *q, double *x, double *res, double *cu, double *s, long int *iu);
00545         static vector<float> lsfit(long int *ks,long int *n, long int *klm2d, long int *iswi, float *q1,double *q, double *x, double *res, double *cu, double *s,long int *iu);
00546         static void cl1(long int *k, long int *l, long int *m, long int *n, long int *klm2d,double *q, double *x, double *res, double *cu, long
00547         int *iu, double *s);
00548         static float eval(char * images,EMData * img, vector<int> S,int N, int K,int size);
00549 
00550         /*  VORONOI DIAGRAM */
00551         static vector<double> vrdg(const vector<float>& ph, const vector<float>& th);
00552         static void hsortd(double *theta,double *phi,int *key,int len,int option);
00553         static void voronoidiag(double *theta,double *phi,double* weight,int n);
00554         /*static void angstep(double* thetast,int len);*/
00555         /*static void voronoi(double *phi,double *theta,double *weight,int lenw,int low,int medium,int nt,int last);*/
00556         static void voronoi(double *phi,double *theta,double *weight, int nt);
00557         static void disorder2(double *x,double *y,int *key,int len);
00558         static void ang_to_xyz(double *x,double *y,double *z,int len);
00559         static void flip23(double *x,double *y,double *z,int *key,int k,int len);
00560         struct tmpstruct{
00561                 double theta1,phi1;
00562                 int key1;
00563                 };
00564         static bool cmp1(tmpstruct tmp1,tmpstruct tmp2);
00565         static bool cmp2(tmpstruct tmp1,tmpstruct tmp2);
00566         /**********************************************************/
00567         /* ######### STRIDPACK USED COMMANDS FOR VORONOI #########################*/
00568         static int trmsh3_(int *n0, double *tol, double *x, double *y, double *z__, int *n, int *list, int *lptr,
00569                int *lend, int *lnew, int *indx, int *lcnt, int *near__, int *next, double *dist, int *ier);
00570         static double areav_(int *k, int *n, double *x, double *y, double *z__, int *list, int *lptr, int *lend, int *ier);
00571         /**********************************************************/
00572         /* ######### STRIDPACK USED COMMANDS FOR VORONOI #########################*/
00573 
00574     /*  Various operation on images */
00575         /* out = img + scalar * img1  */
00576         static EMData* madn_scalar(EMData* img, EMData* img1, float scalar);
00577         /* out = scalar * img  */
00578         static EMData* mult_scalar(EMData* img, float scalar);
00579         /* out = img + img1  */
00580         static EMData* addn_img(EMData* img, EMData* img1);
00581         /* out = img - img1  */
00582         static EMData* subn_img(EMData* img, EMData* img1);
00583         /* out = img * img1  */
00584         static EMData* muln_img(EMData* img, EMData* img1);
00585         /* out = img / img1  */
00586         static EMData* divn_img(EMData* img, EMData* img1);
00587         /* img /= Re(img1) with zero check  */
00588         static EMData* divn_filter(EMData* img, EMData* img1);
00589 
00590         /* img += scalar * img1 */
00591         static void mad_scalar(EMData* img, EMData* img1, float scalar);
00592         /* img *= scalar  */
00593         static void mul_scalar(EMData* img, float scalar);
00594         /* img += img1  */
00595         static void add_img(EMData* img, EMData* img1);
00596         /* img += img1**2  */
00597         static void add_img2(EMData* img, EMData* img1);
00598         /* img -= img1  */
00599         static void sub_img(EMData* img, EMData* img1);
00600         /* img *= img1  */
00601         static void mul_img(EMData* img, EMData* img1);
00602         /* img /= img1  */
00603         static void div_img(EMData* img, EMData* img1);
00604         /* img /= Re(img1) with zero check  */
00605         static void div_filter(EMData* img, EMData* img1);
00606         /* pack absolute values of complex image into  real image with addition of Friedel part  */
00607         static EMData* pack_complex_to_real(EMData* img);
00608 private:
00609         static float ang_n(float peakp, string mode, int maxrin); //this function is used by apmq()
00610 public:
00611         static vector<float> multiref_polar_ali_2d(EMData* image, const vector< EMData* >& crefim,
00612                 float xrng, float yrng, float step, string mode,
00613                 vector< int >numr, float cnx, float cny);
00614         static vector<float> multiref_polar_ali_2d_nom(EMData* image, const vector< EMData* >& crefim,
00615                 float xrng, float yrng, float step, string mode,
00616                 vector< int >numr, float cnx, float cny);
00617         static vector<float> multiref_polar_ali_2d_local(EMData* image, const vector< EMData* >& crefim,
00618                 float xrng, float yrng, float step, float ant, string mode,
00619                 vector< int >numr, float cnx, float cny);
00620         static vector<float> multiref_polar_ali_2d_local_psi(EMData* image, const vector< EMData* >& crefim,
00621                 float xrng, float yrng, float step, float ant, float psi_max, string mode,
00622                 vector< int >numr, float cnx, float cny);
00623 
00624         static void multiref_peaks_ali2d(EMData* image, EMData* crefim,
00625                 float xrng, float yrng, float step, string mode,
00626                 vector< int >numr, float cnx, float cny, EMData* peaks, EMData* peakm);
00627 
00628         static void multiref_peaks_compress_ali2d(EMData* image, EMData* crefim, float xrng, float yrng,
00629              float step, string mode, vector<int>numr, float cnx, float cny, EMData *peaks, EMData *peakm,
00630              EMData *peaks_compress, EMData *peakm_compress);
00631 
00632         static vector<float> ali2d_ccf_list(EMData* image, EMData* crefim, float xrng, float yrng,
00633              float step, string mode, vector<int>numr, float cnx, float cny, double T);
00634      /*
00635         static void multiref_peaks_ali(EMData* image, const vector< EMData* >& crefim,
00636                 float xrng, float yrng, float step, string mode,
00637                 vector< int >numr, float cnx, float cny, EMData* peaks, EMData* peakm,
00638                     int nphi, int ntheta);
00639 */
00640         static vector<float> twoD_fine_ali(EMData* image, EMData *refim, EMData* mask, float ang, float sxs, float sys);
00641 
00642         static vector<float> twoD_fine_ali_G(EMData* image, EMData *refim, EMData* mask, Util::KaiserBessel& kb, float ang, float sxs, float sys);
00643 
00644         static vector<float> twoD_to_3D_ali(EMData* volft, Util::KaiserBessel& kb, EMData *refim, EMData* mask, float phi, float theta, float psi, float sxs, float sxy);
00645 
00646         static vector<float> twoD_fine_ali_SD(EMData* image, EMData *refim, EMData* mask, float ang, float sxs, float sys);
00647 
00648         static float ccc_images(EMData *, EMData *, EMData *, float , float , float );
00649 
00650         static vector<float> twoD_fine_ali_SD_G(EMData* image, EMData *refim, EMData* mask, Util::KaiserBessel& kb, float ang, float sxs, float sys);
00651 
00652         static float ccc_images_G(EMData* image, EMData* refim, EMData* mask, Util::KaiserBessel& kb, float ang, float sx, float sy);
00653 
00654         static EMData* move_points(EMData* img,  float qprob, int ri, int ro);
00655 
00656         static EMData* get_biggest_cluster( EMData* mg );
00657 
00658         //static EMData* ctf_img(int nx, int ny, int nz, float dz, float ps, float voltage=300.0f,float cs=2.0f,float wgh=0.1f,float b_factor=0.0f,float dza=0.0f,float azz=0.0f,float sign=-1.0f);
00659         static EMData* ctf_img(int nx, int ny, int nz, float dz, float ps, float voltage,float cs,float wgh,float b_factor,float dza,float azz,float sign);
00660 
00661         static inline int mono(int k1, int k2) {
00662 #ifdef _WIN32
00663                 int  mk = _cpp_max(k1,k2);
00664                 return  _cpp_min(k1,k2) + mk*(mk-1)/2;
00665 #else
00666                 int  mk = std::max(k1,k2);
00667                 return  std::min(k1,k2) + mk*(mk-1)/2;
00668 #endif  //_WIN32
00669         }
00670 
00671         static inline int nint180(float arg) {
00672             int res = int(arg + 180.5) - 180;
00673             return res;
00674         }
00675 
00676         static vector<float> cluster_pairwise(EMData* d, int K, float T, float F);
00677         //static vector<float> cluster_equalsize(EMData* d, int m);
00678         static vector<float> cluster_equalsize(EMData* d);
00679         static vector<float> vareas(EMData* d);
00680         static EMData* get_slice(EMData *vol, int dim, int index);
00681         static void image_mutation(EMData *img, float mutation_rate);
00682         /*
00683                         To restrict the value to [0, nx)
00684         */
00685         static inline float restrict1(float x, int nx) {
00686                 while ( x < 0.0f )        x += nx;
00687                 while ( x >= (float)(nx) )  x -= nx;
00688                 return x;
00689         }
00690 
00691 #endif  //util__sparx_h__

Generated on Sat Nov 21 02:19:17 2009 for EMAN2 by  doxygen 1.5.6