EMAN2
emdata_core.h
Go to the documentation of this file.
1/*
2 * Author: Steven Ludtke, 04/10/2003 (sludtke@bcm.edu)
3 * Copyright (c) 2000-2006 Baylor College of Medicine
4 *
5 * This software is issued under a joint BSD/GNU license. You may use the
6 * source code in this file under either license. However, note that the
7 * complete EMAN2 and SPARX software packages have some GPL dependencies,
8 * so you are responsible for compliance with the licenses of these packages
9 * if you opt to use BSD licensing. The warranty disclaimer below holds
10 * in either instance.
11 *
12 * This complete copyright notice must be included in any revised version of the
13 * source code. Additional authorship citations may be added, but existing
14 * author citations must be preserved.
15 *
16 * This program is free software; you can redistribute it and/or modify
17 * it under the terms of the GNU General Public License as published by
18 * the Free Software Foundation; either version 2 of the License, or
19 * (at your option) any later version.
20 *
21 * This program is distributed in the hope that it will be useful,
22 * but WITHOUT ANY WARRANTY; without even the implied warranty of
23 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
24 * GNU General Public License for more details.
25 *
26 * You should have received a copy of the GNU General Public License
27 * along with this program; if not, write to the Free Software
28 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
29 *
30 * */
31
36#ifndef emdata__core_h__
37#define emdata__core_h__
38
39public:
43EMData *copy() const;
44
45
49EMData *copy_head() const;
50
51
56void add(float f,int keepzero=0);
57
58
64void add(const EMData & image);
65
71void addsquare(const EMData & image);
72
73
77void sub(float f);
78
79
84void sub(const EMData & image);
85
91void subsquare(const EMData & image);
92
93
97void mult(int n)
98{
99 mult((float)n);
100}
101
102
106void mult(float f);
107
108
116void mult(const EMData & image, bool prevent_complex_multiplication=false);
117
126void mult_ri(const EMData & image);
127
128
129void mult_complex_efficient(const EMData & em, const int radius);
130
134void div(float f);
135
136
142void div(const EMData & image);
143
151void update_min(const EMData & image);
152
153
155void to_zero();
156
157
159void to_one();
160
162void to_value(const float& value);
163
174float dot(EMData * with);
175
176
183EMData *get_row(int row_index) const;
184
185
192void set_row(const EMData * data, int row_index);
193
194
201EMData *get_col(int col_index) const;
202
203
210void set_col(const EMData * data, int col_index);
211
212
221inline float get_value_at(int x, int y, int z) const
222{
223 return get_data()[(size_t)x + (size_t)y * (size_t)nx + (size_t)z * (size_t)nxy];
224}
225
229inline float get_value_at_index(size_t i) const
230{
231 return *(rdata + i);
232}
233
241inline float get_value_at(int x, int y) const
242{
243 return get_data()[x + y * nx];
244}
245
246
254inline float get_value_at(size_t i) const
255{
256 return get_data()[i];
257}
258
270std::complex<float> get_complex_at(const int &x,const int &y) const;
271
284std::complex<float> get_complex_at(const int &x,const int &y,const int &z) const;
285
298size_t get_complex_index(const int &x,const int &y,const int &z) const;
299
300size_t get_complex_index(int x,int y,int z,const int &subx0,const int &suby0,const int &subz0,const int &fullnx,const int &fullny,const int &fullnz) const;
301
302inline size_t get_complex_index_fast(const int &x,const int &y,const int &z) const {
303// if (abs(x)>=nx/2 || abs(y)>ny/2 || abs(z)>nz/2) return nxyz;
304 if (x<0) {
305 return (size_t)x*-2+(y<=0?-y:ny-y)*(size_t)nx+(z<=0?-z:nz-z)*(size_t)nxy;
306 }
307 return x*2+(y<0?ny+y:y)*(size_t)nx+(z<0?nz+z:z)*(size_t)nxy;
308}
309
318inline void set_complex_at_idx(const int &x,const int &y,const int &z,const std::complex<float> &val) {
319 size_t idx=x*2+y*(size_t)nx+z*(size_t)nxy;
320 rdata[idx]=(float)val.real();
321 rdata[idx+1]=(float)val.imag();
322}
323
336void set_complex_at(const int &x,const int &y,const std::complex<float> &val);
337
351void set_complex_at(const int &x,const int &y,const int &z,const std::complex<float> &val);
352
366size_t add_complex_at(const int &x,const int &y,const int &z,const std::complex<float> &val);
367
368inline size_t add_complex_at_fast(const int &x,const int &y,const int &z,const std::complex<float> &val) {
369//if (x>=nx/2 || y>ny/2 || z>nz/2 || x<=-nx/2 || y<-ny/2 || z<-nz/2) return nxyz;
370if (abs(x)>=nx/2 || abs(y)>ny/2 || abs(z)>nz/2) return nxyz;
371
372//if (x==0 && abs(y)==16 && abs(z)==1) printf("## %d %d %d\n",x,y,z);
373size_t idx;
374// for x=0, we need to insert the value in 2 places
375if (x==0) {
376 if (y==0 && z==0) {
377 rdata[0]+=(float)val.real();
378 rdata[1]=0;
379 return 0;
380 }
381 // complex conjugate in x=0 plane
382 size_t idx=(y<=0?-y:ny-y)*(size_t)nx+(z<=0?-z:nz-z)*(size_t)nxy;
383// if (idx==16*34+1*34*32) printf("a %d %d %d\t%1.5f+%1.5fi\t%1.5f+%1.5fi\n",x,y,z,val.real(),val.imag(),rdata[idx],rdata[idx+1]);
384 rdata[idx]+=(float)val.real();
385 rdata[idx+1]+=(float)-val.imag();
386}
387if (abs(x)==nx/2-1) {
388 if (y==0 && z==0) {
389 rdata[nx-2]+=(float)val.real();
390 rdata[nx-1]=0;
391 return nx-2;
392 }
393 // complex conjugate in x=0 plane
394 size_t idx=nx-2+(y<=0?-y:ny-y)*(size_t)nx+(z<=0?-z:nz-z)*(size_t)nxy;
395// if (idx==16*34+1*34*32) printf("b %d %d %d\t%1.5f+%1.5fi\t%1.5f+%1.5fi\n",x,y,z,val.real(),val.imag(),rdata[idx],rdata[idx+1]);
396 rdata[idx]+=(float)val.real();
397 rdata[idx+1]+=(float)-val.imag();
398}
399if (x<0) {
400 idx=-x*2+(y<=0?-y:ny-y)*(size_t)nx+(z<=0?-z:nz-z)*(size_t)nxy;
401// if (idx==16*34+1*34*32) printf("c %d %d %d\t%1.5f+%1.5fi\t%1.5f+%1.5fi\n",x,y,z,val.real(),val.imag(),rdata[idx],rdata[idx+1]);
402 rdata[idx]+=(float)val.real();
403 rdata[idx+1]+=-(float)val.imag();
404 return idx;
405}
406
407idx=x*2+(y<0?ny+y:y)*(size_t)nx+(z<0?nz+z:z)*(size_t)nxy;
408//if (idx==16*34+1*34*32) printf("d %d %d %d\t%1.5f+%1.5fi\t%1.5f+%1.5fi\n",x,y,z,val.real(),val.imag(),rdata[idx],rdata[idx+1]);
409rdata[idx]+=(float)val.real();
410rdata[idx+1]+=(float)val.imag();
411
412return idx;
413}
414
426size_t add_complex_at(int x,int y,int z,const int &subx0,const int &suby0,const int &subz0,const int &fullnx,const int &fullny,const int &fullnz,const std::complex<float> &val);
427
437float get_value_at_wrap(int x, int y, int z) const;
438float& get_value_at_wrap(int x, int y, int z);
439
448float get_value_at_wrap(int x, int y) const;
449float& get_value_at_wrap(int x, int y);
450
458float get_value_at_wrap(int x) const;
459float& get_value_at_wrap(int x);
460
465inline float sget_value_at(Vec3i v) { return sget_value_at(v[0],v[1],v[2]); }
466
476float sget_value_at(int x, int y, int z) const;
477
478
487float sget_value_at(int x, int y) const;
488
489
498float sget_value_at(size_t i) const;
499
500
507std::complex<float> get_complex_at_interp(float x, float y) const;
508
516std::complex<float> get_complex_at_ginterp(float x, float y) const;
517
525std::complex<float> get_complex_at_3ginterp(float x, float y) const;
526
527
535float sget_value_at_interp(float x, float y) const;
536
537
546float sget_value_at_interp(float x, float y, float z) const;
547
552inline void set_value_at(Vec3i loc,float val) { set_value_at(loc[0],loc[1],loc[2],val); }
553
563inline void set_value_at(int x, int y, int z, float v)
564{
565 if( x>=nx || x<0 )
566 {
567 throw OutofRangeException(0, nx-1, x, "x dimension index");
568 }
569 else if( y>=ny || y<0 )
570 {
571 throw OutofRangeException(0, ny-1, y, "y dimension index");
572 }
573 else if( z>=nz || z<0 )
574 {
575 throw OutofRangeException(0, nz-1, z, "z dimension index");
576 }
577 else
578 {
579 get_data()[(size_t)x + (size_t)y * (size_t)nx + (size_t)z * (size_t)nxy] = v;
580 update();
581 }
582}
583
584
594inline void mult_value_at_fast(int x, int y, int z, float v)
595{
596 get_data()[(size_t)x + (size_t)y * (size_t)nx + (size_t)z * (size_t)nxy] *= v;
597 update();
598}
599
609inline void set_value_at_fast(int x, int y, int z, float v)
610{
611 get_data()[(size_t)x + (size_t)y * (size_t)nx + (size_t)z * (size_t)nxy] = v;
612 update();
613}
614
621inline void set_value_at_index(size_t i, float v)
622{
623 *(rdata + i) = v;
624}
625
634inline void set_value_at(int x, int y, float v)
635{
636 if( x>=nx || x<0 )
637 {
638 throw OutofRangeException(0, nx-1, x, "x dimension index");
639 }
640 else if( y>=ny || y<0 )
641 {
642 throw OutofRangeException(0, ny-1, y, "y dimension index");
643 }
644 else
645 {
646 get_data()[x + y * nx] = v;
647 update();
648
649 }
650}
651
652
660inline void set_value_at_fast(int x, int y, float v)
661{
662 get_data()[x + y * nx] = v;
663 update();
664}
665
666
674inline void set_value_at(int x, float v)
675{
676 if( x>=nx || x<0 )
677 {
678 throw OutofRangeException(0, nx-1, x, "x dimension index");
679 }
680 else
681 {
682 get_data()[x] = v;
683
684 update();
685 }
686}
687
694inline void set_value_at_fast(int x, float v)
695{
696 get_data()[x] = v;
697
698 update();
699}
700
701
706
710void free_rdata();
711
712EMData & operator+=(float n);
713EMData & operator-=(float n);
714EMData & operator*=(float n);
715EMData & operator/=(float n);
716
717EMData & operator+=(const EMData & em);
718EMData & operator-=(const EMData & em);
719EMData & operator*=(const EMData & em);
720EMData & operator/=(const EMData & em);
721
722bool operator==(const EMData& that) const;
724bool equal(const EMData& that) const;
725
727inline float& operator()(const int ix, const int iy, const int iz) const {
728 ptrdiff_t pos = (size_t)(ix-xoff) + ((iy-yoff) + (size_t)(iz-zoff)*ny)*nx;
729#ifdef BOUNDS_CHECKING
730 if (pos < 0 || pos >= (size_t)nx*ny*nz) {
731 throw OutofRangeException(0, (size_t)nx*ny*nz-1, pos, "EMData");
732 }
733#endif // BOUNDS_CHECKING
734 return *(get_data() + pos);
735}
736
737inline float& operator()(const int ix, const int iy) const {
738 ptrdiff_t pos = (ix - xoff) + (iy-yoff)*nx;
739#ifdef BOUNDS_CHECKING
740 if (pos < 0 || pos >= (size_t)nx*ny*nz)
741 {
742 throw OutofRangeException(0, (size_t)nx*ny*nz-1, pos, "EMData");
743 }
744#endif // BOUNDS_CHECKING
745 return *(get_data() + pos);
746}
747
748
749inline float& operator()(const size_t ix) const {
750 ptrdiff_t pos = ix - xoff;
751#ifdef BOUNDS_CHECKING
752 if (pos < 0 || pos >= (size_t)nx*ny*nz)
753 throw OutofRangeException(0, (size_t)nx*ny*nz-1, pos, "EMData");
754#endif // BOUNDS_CHECKING
755 return *(get_data() + pos);
756}
757
758
760void set_array_offsets(const int xoff_=0, const int yoff_=0,
761 const int zoff_=0) {
762 xoff=xoff_; yoff=yoff_; zoff=zoff_;
763}
764
765
766void set_array_offsets(vector<int> offsets) {
767 set_array_offsets(offsets[0],offsets[1],offsets[2]);
768}
769
770
771vector<int> get_array_offsets() {
772 vector<int> offsets;
773 offsets.push_back(xoff);
774 offsets.push_back(yoff);
775 offsets.push_back(zoff);
776 return offsets;
777}
778
779
781std::complex<float>& cmplx(const int ix, const int iy, const int iz) {
782 ptrdiff_t pos = 2*(ix-xoff)+((iy-yoff)+(iz-zoff)*ny)*(size_t)nx;
783#ifdef BOUNDS_CHECKING
784 if (pos < 0 || pos >= (size_t)nx*ny*nz)
785 throw OutofRangeException(0, (size_t)nx*ny*nz-1, pos, "EMData");
786#endif // BOUNDS_CHECKING
787 float* begin = get_data() + pos;
788 return *(reinterpret_cast<std::complex<float>* >(begin));
789}
790
791
792std::complex<float>& cmplx(const int ix, const int iy) {
793 ptrdiff_t pos = 2*(ix-xoff)+(iy-yoff)*nx;
794#ifdef BOUNDS_CHECKING
795 if (pos < 0 || pos >= (size_t)nx*ny*nz)
796 throw OutofRangeException(0, (size_t)nx*ny*nz-1, pos, "EMData");
797#endif // BOUNDS_CHECKING
798 float* begin = get_data() + pos;
799 return *(reinterpret_cast<std::complex<float>* >(begin));
800}
801
802
803std::complex<float>& cmplx(const int ix) {
804 ptrdiff_t pos = 2*(ix-xoff);
805#ifdef BOUNDS_CHECKING
806 if (pos < 0 || pos >= (size_t)nx*ny*nz)
807 throw OutofRangeException(0, (size_t)nx*ny*nz-1, pos, "EMData");
808#endif // BOUNDS_CHECKING
809 float* begin = get_data() + pos;
810 return *(reinterpret_cast<std::complex<float>* >(begin));
811}
812
813
819EMData * power(int n) const;
820
825EMData * sqrt() const;
826
827
833EMData * log() const;
834
835
841EMData * log10() const;
842
843
848EMData * real() const;
849
850
856EMData * imag() const;
857
863EMData * absi() const;
864
865
870EMData * amplitude() const;
871
872
877EMData * phase() const;
878
879
885EMData * real2complex(float img = 0.0f) const;
886
887#endif //emdata__core_h__
#define rdata(i)
Definition: analyzer.cpp:592
void addsquare(const EMData &image)
add the squared value of each pixel from a same-size image to this image.
float sget_value_at_interp(float x, float y) const
Get pixel density value at interpolation of (x,y).
void set_value_at_index(size_t i, float v)
Set the pixel density value at index.
Definition: emdata_core.h:621
std::complex< float > get_complex_at_interp(float x, float y) const
Gets bilinear interpolated complex values.
EMData * copy() const
This file is a part of "emdata.h", to use functions in this file, you should "#include "emdata....
size_t add_complex_at(const int &x, const int &y, const int &z, const std::complex< float > &val)
Add complex<float> value at x,y,z.
void to_zero()
Set all the pixel value = 0.
EMData & operator+=(float n)
size_t get_complex_index(const int &x, const int &y, const int &z) const
Get complex<float> index for coords x,y,z.
EMData * get_col(int col_index) const
Get one column of a 2D images.
std::complex< float > & cmplx(const int ix, const int iy, const int iz)
Return reference to complex elements.
Definition: emdata_core.h:781
EMData * log() const
return natural logarithm image for a image
void mult(int n)
multiply an integer number to each pixel value of the image.
Definition: emdata_core.h:97
void set_complex_at_idx(const int &x, const int &y, const int &z, const std::complex< float > &val)
Set complex<float> value at x,y,z without reinterpreting the coordinates.
Definition: emdata_core.h:318
void set_value_at(Vec3i loc, float val)
set_value_at with Vec3i
Definition: emdata_core.h:552
EMData * absi() const
For a real image, it returns a same size image with abs() of each pixel.
void to_value(const float &value)
set all the pixel values to a value.
bool equal(const EMData &that) const
compare the equality of two EMData object based on their pixel values
void set_array_offsets(const int xoff_=0, const int yoff_=0, const int zoff_=0)
Set the array offsets.
Definition: emdata_core.h:760
EMData * power(int n) const
return a image to the power of n
vector< int > get_array_offsets()
Definition: emdata_core.h:771
float get_value_at_wrap(int x, int y, int z) const
Get the pixel density value at coordinates (x,y,z).
void add(float f, int keepzero=0)
add a number to each pixel value of the image.
void sub(float f)
subtract a float number to each pixel value of the image.
EMData * sqrt() const
return square root of current image
void to_one()
set all the pixel values = 1.
float get_value_at(int x, int y, int z) const
Get the pixel density value at coordinates (x,y,z).
Definition: emdata_core.h:221
EMData * real2complex(float img=0.0f) const
create a complex image from a real image, this complex image is in real/imaginary format
void mult_value_at_fast(int x, int y, int z, float v)
Multiplies the pixel density value at coordinates (x,y,z).
Definition: emdata_core.h:594
float sget_value_at(Vec3i v)
Vec3i version of save routines below.
Definition: emdata_core.h:465
EMData * log10() const
return base 10 logarithm image for a image
size_t add_complex_at_fast(const int &x, const int &y, const int &z, const std::complex< float > &val)
Definition: emdata_core.h:368
float dot(EMData *with)
Dot product 2 images.
EMData * amplitude() const
return amplitude part of a complex image as a real image format
void set_row(const EMData *data, int row_index)
Set one row of a 1D/2D image.
void mult_ri(const EMData &image)
multiply each complex RI pixel of this image with each pixel of some other same-size image.
EMData * imag() const
return imaginary part of a complex image as a real image format.
std::complex< float > get_complex_at_3ginterp(float x, float y) const
Gets 3x3 Gaussian interpolated complex values note that with Gaussian interpolation,...
float get_value_at_index(size_t i) const
Get the pixel density value at index i.
Definition: emdata_core.h:229
float & operator()(const int ix, const int iy, const int iz) const
Overload operator() for array indexing.
Definition: emdata_core.h:727
void set_complex_at(const int &x, const int &y, const std::complex< float > &val)
Set complex<float> value at x,y.
void free_memory()
Free memory associated with this EMData Called in destructor and in assignment operator.
EMData * real() const
return real part of a complex image as a real image format, if this image is a real image,...
size_t get_complex_index_fast(const int &x, const int &y, const int &z) const
Definition: emdata_core.h:302
void mult_complex_efficient(const EMData &em, const int radius)
std::complex< float > get_complex_at(const int &x, const int &y) const
Get complex<float> value at x,y.
void subsquare(const EMData &image)
subtract the squared value of each pixel from a same-size image to this image.
EMData & operator*=(float n)
void update_min(const EMData &image)
Replaces the value of each pixel with the minimum of the current value and the value in the provided ...
void set_value_at_fast(int x, int y, int z, float v)
Set the pixel density value at coordinates (x,y,z).
Definition: emdata_core.h:609
EMData * phase() const
return phase part of a complex image as a real image format
void div(float f)
make each pixel value divided by a float number.
EMData * copy_head() const
Make an image with a copy of the current image's header.
std::complex< float > get_complex_at_ginterp(float x, float y) const
Gets 2x2 Gaussian interpolated complex values note that with Gaussian interpolation,...
void free_rdata()
Free rdata memory associated with this EMData Called in CUDA.
Definition: emdata_core.cpp:79
void set_col(const EMData *data, int col_index)
Set one column of a 2D image.
EMData & operator/=(float n)
bool operator==(const EMData &that) const
EMData & operator-=(float n)
EMData * get_row(int row_index) const
Get one row of a 1D/2D image.
void update()
Mark EMData as changed, statistics, etc will be updated at need.
float * get_data() const
Get the image pixel density data in a 1D float array.
#define OutofRangeException(low, high, input, objname)
Definition: exception.h:334
Vec3< int > Vec3i
Definition: vec3.h:694
#define y(i, j)
Definition: projector.cpp:1516
#define x(i)
Definition: projector.cpp:1517