Commit e9a1b9742e9c2d44cf3c233d03a6fe945c1a62f0

Authored by Pavel Govyadinov
1 parent ae05c3e4

imlemented Dr. Mayeriches fix for the memory leak. Removed extranous comments

Showing 1 changed file with 35 additions and 31 deletions   Show diff stats
stim/image/image.h
... ... @@ -24,6 +24,8 @@ class image{
24 24 size_t Y() const { return R[2]; }
25 25 size_t C() const { return R[0]; }
26 26  
  27 + size_t bytes(){ return size() * sizeof(T); }
  28 +
27 29 void init(){ //initializes all variables, assumes no memory is allocated
28 30 memset(R, 0, sizeof(size_t) * 3); //set the resolution and number of channels to zero
29 31 img = NULL;
... ... @@ -31,6 +33,8 @@ class image{
31 33  
32 34 void unalloc(){ //frees any resources associated with the image
33 35 if(img) free(img); //if memory has been allocated, free it
  36 + img=NULL;
  37 +
34 38 }
35 39  
36 40  
... ... @@ -40,15 +44,17 @@ class image{
40 44 }
41 45  
42 46 void allocate(){
43   - img = (T*) malloc( sizeof(T) * R[0] * R[1] * R[2] ); //allocate memory
  47 + unalloc();
  48 + img = (T*) malloc( bytes() ); //allocate memory
  49 + memset(img, 0, bytes());
44 50 }
45 51  
46 52 void allocate(size_t x, size_t y, size_t c){ //allocate memory based on the resolution
  53 + unalloc();
47 54 R[0] = c; R[1] = x; R[2] = y; //set the resolution
48 55 allocate(); //allocate memory
49 56 }
50 57  
51   - size_t bytes(){ return size() * sizeof(T); }
52 58  
53 59 size_t idx(size_t x, size_t y, size_t c = 0){
54 60 return y * C() * X() + x * C() + c;
... ... @@ -89,36 +95,33 @@ public:
89 95 image(){ init(); } //initialize all variables to zero, don't allocate any memory
90 96  
91 97 /// Constructor with a filename - loads the specified file
92   - image(std::string filename){ //constructor initialize the image with an image file
  98 + image(std::string filename) : image(){ //constructor initialize the image with an image file
93 99 load(filename);
94 100 }
95 101  
96 102 /// Create a new image from scratch given a number of samples and channels
97   - image(size_t x, size_t y = 1, size_t c = 1){
  103 + image(size_t x, size_t y = 1, size_t c = 1) : image(){
  104 + init();
98 105 allocate(x, y, c);
99 106 }
100 107  
101 108 /// Create a new image with the data given in 'data'
102   - image(T* data, size_t x, size_t y, size_t c = 1){
  109 + image(T* data, size_t x, size_t y, size_t c = 1) : image(){
  110 + init();
103 111 allocate(x, y, c);
104 112 memcpy(img, data, bytes());
105 113 }
106 114  
107 115 /// Copy constructor - duplicates an image object
108   - image(const stim::image<T>& I){
  116 + image(const stim::image<T>& I) : image(){
  117 + init();
109 118 allocate(I.X(), I.Y(), I.C());
110   - //allocate(I.R[1], I.R[2], I.R[0]);
111 119 memcpy(img, I.img, bytes());
112 120 }
113 121  
114 122 /// Destructor - clear memory
115   -// ~image(){
116   -// free(img);
117   -// }
118   -
119   - void clear_exp(){ //clears all image data
120   - unalloc();
121   -
  123 + ~image(){
  124 + free(img);
122 125 }
123 126  
124 127 stim::image<T> operator=(const stim::image<T>& I){
... ... @@ -142,24 +145,14 @@ public:
142 145 if(C() == 1)
143 146 {
144 147 //if this is a single-color image, just copy the data
145   -/*
146   - THIS DOES NOT WORK PROPERLY.
147   - YOU CANNOT DO MEMCPY LIKE THIS BECAUSE IT CORRUPTS THE POINTREF MECHANIC IN OPENCV AND NEVER ACTUALLY CREATES A DEEP COPY BUT TAKES UP THE MEMORY.
148   - TO TEST run and compile pseudocode
149   - stim::image<unsigned char> I;
150   - for(int i = 0; i < file_list.size(); i++)
151   - I.load(file_list[i].srt())
152   -
153   -
154   - You will run out of memory.
155   -*/
156 148 memcpy(img, cv_ptr, bytes());
157   -// img = cvImage.data;
158 149 }
159   - if(C() == 3) //if this is a 3-color image, OpenCV uses BGR interleaving
  150 + if(C() == 3)
  151 + { //if this is a 3-color image, OpenCV uses BGR interleaving
160 152 set_interleaved_bgr(cv_ptr, X(), Y());
  153 + }
161 154  
162   -// cvImage.deallocate();
  155 + cvImage.release();
163 156 }
164 157  
165 158 //save a file
... ... @@ -352,6 +345,17 @@ public:
352 345  
353 346 return r; //return the inverted image
354 347 }
  348 +
  349 + /// Invert an image by calculating I1 = alpha - I0, where alpha is the maximum image value
  350 + image<T> invert(){
  351 + size_t N = size(); //calculate the total number of values in the image
  352 + image<T> r(X(), Y(), C()); //allocate space for the resulting image
  353 + T white_val = maxv();
  354 + for(size_t n = 0; n < N; n++)
  355 + r.img[n] = white_val - img[n]; //perform the inversion
  356 +
  357 + return r; //return the inverted image
  358 + }
355 359  
356 360 ///crops the image from x1 to x0 and y1 to y0 and returns a new (smaller) image.
357 361 ///Untested
... ... @@ -361,12 +365,12 @@ public:
361 365 image<T> ret(x1-x0, y1-y0, C());
362 366 int newWidth = x1-x0;
363 367 int destidx, srcidx;
364   -// for(int i = 0; i < (y1-y0); i++)
  368 + for(int i = 0; i < (y1-y0); i++)
365 369 {
366 370 destidx = i*newWidth*C(); ///destination index one per each row
367 371 srcidx = ((i+(y0))*X()+x0)*C(); ///source index, one per each row.
368   - ret.set_interleaved_rgb(img[srcidx], newWidth, y1-y0, C());
369   - memcpy(&ret.img[destidx], &buffer[srcidx], sizeof(T)*newWidth*C());
  372 +// ret.set_interleaved_rgb(img[srcidx], newWidth, y1-y0, C());
  373 + memcpy(&ret.img[destidx], &img[srcidx], sizeof(T)*newWidth*C());
370 374 }
371 375  
372 376 // for(int i = 0; i < (x1 -x0); i++)
... ...