Advertisement
Guest User

Untitled

a guest
Mar 28th, 2020
163
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 12.06 KB | None | 0 0
  1. #include <iostream>
  2. #include <string>
  3. #include <sstream>
  4. #include <fstream>
  5. #include <cmath>
  6. #include "functions.h"
  7.  
  8. using namespace std;
  9.  
  10. Pixel** createImage(int width, int height) {
  11. cout << "Start createImage... " << endl;
  12.  
  13. // Create a one dimensional array on the heap of pointers to Pixels
  14. // that has width elements (i.e. the number of columns)
  15. Pixel** image = new Pixel*[width];
  16.  
  17. bool fail = false;
  18.  
  19. for (int i=0; i < width; ++i) { // loop through each column
  20. // assign that column to a one dimensional array on the heap of Pixels
  21. // that has height elements (i.e. the number of rows)
  22. image[i] = new Pixel[height];
  23.  
  24. if (image[i] == nullptr) { // failed to allocate
  25. fail = true;
  26. }
  27. }
  28.  
  29. if (fail) { // if any allocation fails, clean up and avoid memory leak
  30. // deallocate any arrays created in for loop
  31. for (int i=0; i < width; ++i) {
  32. delete [] image[i]; // deleting nullptr is not a problem
  33. }
  34. delete [] image; // dlete array of pointers
  35. return nullptr;
  36. }
  37.  
  38. // initialize cells
  39. //cout << "Initializing cells..." << endl;
  40. for (int row=0; row<height; ++row) {
  41. for (int col=0; col<width; ++col) {
  42. //cout << "(" << col << ", " << row << ")" << endl;
  43. image[col][row] = { 0, 0, 0 };
  44. }
  45. }
  46. cout << "End createImage... " << endl;
  47. return image;
  48. }
  49.  
  50. void deleteImage(Pixel** image, int width) {
  51. cout << "Start deleteImage..." << endl;
  52. // avoid memory leak by deleting the array
  53. for (int i=0; i<width; ++i) {
  54. delete [] image[i]; // delete each individual array placed on the heap
  55. }
  56. delete [] image;
  57. image = nullptr;
  58. }
  59.  
  60. int* createSeam(int length) {
  61. int* arr = new int[length];
  62. for(int i = 0; i < length; i++) {
  63. arr[i] = 0;
  64. }
  65. return arr;
  66.  
  67. return nullptr;
  68. }
  69.  
  70. void deleteSeam(int* seam) {
  71. delete [] seam;
  72. }
  73.  
  74. bool loadImage(string filename, Pixel** image, int width, int height) {
  75. ifstream ifs(filename);
  76. if(!ifs.is_open()) {
  77. cout << "Error: failed to open input file - " << filename;
  78. return false;
  79. }
  80.  
  81. char type[3];
  82. ifs >> type;
  83. if((toupper(type[0] != 'P')) || (type[1] != '3')) {
  84. cout << "Error: type is " << type << " instead of P3";
  85. return false;
  86. }
  87.  
  88. int w =0;
  89. int h =0;
  90. ifs >> w >> h;
  91. if(!ifs.good()) {
  92. cout << "Error: read non-integer value" << endl;
  93. return false;
  94. }
  95. if(w != width) {
  96. cout <<"Error: input width (" << width << ") does not match value in file (" << w << ")" << endl;
  97. return false;
  98. }
  99. if(h != height) {
  100. cout << "Error: input height (" << height << ") does not match value in file ("<< h << ")" << endl;
  101. return false;
  102. }
  103. int colorMax = 0;
  104. ifs >> colorMax;
  105. if(colorMax != 255) {
  106. cout << "Error: file is not using RGB color values."<<endl;
  107. return false;
  108. }
  109.  
  110. int fr;
  111. int fg;
  112. int fb;
  113.  
  114. for(int i = 0; i < height; i++) {
  115. for(int j = 0; j < width; j++ ) {
  116. if(ifs.eof()) {
  117. cout << "Error: not enough color values" << endl;
  118. return false;
  119. }
  120.  
  121. ifs >> fr;
  122. if(ifs.eof()) {
  123. cout << "Error: not enough color values" << endl;
  124. return false;
  125. }
  126. if(ifs.fail()) {
  127. cout << "Error: read non-integer value" << endl;
  128. return false;
  129. }
  130. image[j][i].r = fr;
  131.  
  132. ifs >> fg;
  133. if(ifs.eof()) {
  134. cout << "Error: not enough color values" << endl;
  135. return false;
  136. }
  137. if(ifs.fail()) {
  138. cout << "Error: read non-integer value" << endl;
  139. return false;
  140. }
  141. image[j][i].g = fg;
  142.  
  143. ifs >> fb;
  144. if(!ifs.eof() && !ifs.good()) {
  145. cout << "Error: read non-integer value" << endl;
  146. return false;
  147. }
  148.  
  149. if(ifs.eof()) {
  150. cout << "Error: not enough color values" << endl;
  151. }
  152.  
  153. image[j][i].b = fb;
  154.  
  155. if(fb<0 || fb>255){
  156. cout << "Error: invalid color value "<< fb << endl;
  157. return false;
  158. }
  159. if(fg<0 || fg>255){
  160. cout << "Error: invalid color value "<< fg << endl;
  161. return false;
  162. }
  163. if(fr<0 || fr>255){
  164. cout << "Error: invalid color value "<< fr << endl;
  165. return false;
  166. }
  167. }
  168. }
  169.  
  170. string check;
  171. if(!ifs.eof()) {
  172. ifs >> check;
  173. if(check != " ") {
  174. cout << "Error: too many color values";
  175. }
  176. if(ifs.eof()) {
  177. return true;
  178. }
  179. }
  180. ifs.close();
  181. return true;
  182. }
  183.  
  184. bool outputImage(string filename, Pixel** image, int width, int height) {
  185. ofstream ofs(filename);
  186. if(!ofs.is_open()) {
  187. cout << "Error: failed to open output file - " << filename;
  188. return false;
  189. }
  190. ofs << 'P' << '3' << "\n";
  191. ofs << width << " " << height << "\n";
  192. ofs << 255 << "\n";
  193. for(int col = 0; col < width; col++) {
  194. for(int row = 0; row < height; row++) {
  195. ofs <<image[row][col].r << "\n" << image[row][col].g << "\n" << image[row][col].b << "\n";
  196. }
  197. ofs << "\n";
  198. }
  199.  
  200. ofs.close();
  201. return true;
  202. }
  203.  
  204. int energy(Pixel** image, int x, int y, int width, int height) {
  205. if((y>0 && x>0) && (x<width-1 && y<height-1)){
  206. //2, 1
  207. int rx = image[x+1][y].r - image[x-1][y].r;
  208. int gx = image[x+1][y].g - image[x-1][y].g;
  209. int bx = image[x+1][y].b - image[x-1][y].b;
  210.  
  211. int ry = image[x][y-1].r - image[x][y+1].r;
  212. int gy = image[x][y-1].g - image[x][y+1].g;
  213. int by = image[x][y-1].b - image[x][y+1].b;
  214.  
  215. int totX = pow(rx,2) + pow(gx,2) + pow(bx,2);
  216. int totY = pow(ry,2) + pow(gy,2) + pow(by,2);
  217.  
  218. int energy = totX + totY;
  219. return energy;
  220. }
  221. if(x==width-1 && y==0) {
  222. int rx = image[0][0].r - image[x-1][y].r;
  223. int gx = image[0][0].g - image[x-1][y].g;
  224. int bx = image[0][0].b - image[x-1][y].b;
  225.  
  226. int ry = image[x][height-1].r - image[x][y+1].r;
  227. int gy = image[x][height-1].g - image[x][y+1].g;
  228. int by = image[x][height-1].b - image[x][y+1].b;
  229.  
  230. int totX = pow(rx,2) + pow(gx,2) + pow(bx,2);
  231. int totY = pow(ry,2) + pow(gy,2) + pow(by,2);
  232.  
  233. int energy = totX + totY;
  234. return energy;
  235. }
  236. if(x==0 && y==0){
  237. //0,0
  238. int rx = image[1][0].r - image[width-1][0].r;
  239. int gx = image[1][0].g - image[width-1][0].g;
  240. int bx = image[1][0].b - image[width-1][0].b;
  241.  
  242. int ry = image[0][height-1].r - image[0][1].r;
  243. int gy = image[0][height-1].g - image[0][1].g;
  244. int by = image[0][height-1].b - image[0][1].b;
  245.  
  246. int totX = pow(rx,2) + pow(gx,2) + pow(bx,2);
  247. int totY = pow(ry,2) + pow(gy,2) + pow(by,2);
  248.  
  249. int energy = totX + totY;
  250. return energy;
  251. }
  252. if(x==width-1 && y==height-1){
  253. int rx = image[0][y].r - image[x-1][y].r;
  254. int gx = image[0][y].g - image[x-1][y].g;
  255. int bx = image[0][y].b - image[x-1][y].b;
  256.  
  257. int ry = image[x][y-1].r - image[width-1][0].r;
  258. int gy = image[x][y-1].g - image[width-1][0].g;
  259. int by = image[x][y-1].b - image[width-1][0].b;
  260.  
  261. int totX = pow(rx,2) + pow(gx,2) + pow(bx,2);
  262. int totY = pow(ry,2) + pow(gy,2) + pow(by,2);
  263.  
  264. int energy = totX + totY;
  265. return energy;
  266. }
  267. if(x==0 && y==height-1){
  268. int rx = image[1][y].r - image[width-1][y].r;
  269. int gx = image[1][y].g - image[width-1][y].g;
  270. int bx = image[1][y].b - image[width-1][y].b;
  271.  
  272. int ry = image[x][y-1].r - image[0][0].r;
  273. int gy = image[x][y-1].g - image[0][0].g;
  274. int by = image[x][y-1].b - image[0][0].b;
  275.  
  276. int totX = pow(rx,2) + pow(gx,2) + pow(bx,2);
  277. int totY = pow(ry,2) + pow(gy,2) + pow(by,2);
  278.  
  279. int energy = totX + totY;
  280. return energy;
  281. }
  282.  
  283. if(x!=0 && y==0){
  284. int rx = image[x+1][y].r - image[x-1][y].r;
  285. int gx = image[x+1][y].g - image[x-1][y].g;
  286. int bx = image[x+1][y].b - image[x-1][y].b;
  287.  
  288. int ry = image[x][height-1].r - image[x][y+1].r;
  289. int gy = image[x][height-1].g - image[x][y+1].g;
  290. int by = image[x][height-1].b - image[x][y+1].b;
  291.  
  292. int totX = pow(rx,2) + pow(gx,2) + pow(bx,2);
  293. int totY = pow(ry,2) + pow(gy,2) + pow(by,2);
  294.  
  295. int energy = totX + totY;
  296. return energy;
  297. }
  298.  
  299. if(x==0 && y!=0){
  300. int rx = image[x+1][y].r - image[width-1][y].r;
  301. int gx = image[x+1][y].g - image[width-1][y].g;
  302. int bx = image[x+1][y].b - image[width-1][y].b;
  303.  
  304. int ry = image[x][y-1].r - image[x][y+1].r;
  305. int by = image[x][y-1].b - image[x][y+1].b;
  306. int gy = image[x][y-1].g - image[x][y+1].g;
  307.  
  308. int totX = pow(rx,2) + pow(gx,2) + pow(bx,2);
  309. int totY = pow(ry,2) + pow(gy,2) + pow(by,2);
  310.  
  311. int energy = totX + totY;
  312. return energy;
  313. }
  314.  
  315.  
  316.  
  317. if(x==width-1){
  318. int rx = image[0][y].r - image[x-1][y].r;
  319. int gx = image[0][y].g - image[x-1][y].g;
  320. int bx = image[0][y].b - image[x-1][y].b;
  321.  
  322. int ry = image[x][y-1].r - image[x][y+1].r;
  323. int gy = image[x][y-1].g - image[x][y+1].g;
  324. int by = image[x][y-1].b - image[x][y+1].b;
  325.  
  326. int totX = pow(rx,2) + pow(gx,2) + pow(bx,2);
  327. int totY = pow(ry,2) + pow(gy,2) + pow(by,2);
  328.  
  329. int energy = totX + totY;
  330. return energy;
  331.  
  332. }
  333. if(y==height-1){
  334. int rx = image[x+1][y].r - image[x-1][y].r;
  335. int gx = image[x+1][y].g - image[x-1][y].g;
  336. int bx = image[x+1][y].b - image[x-1][y].b;
  337.  
  338. int ry = image[x][y-1].r - image[x][0].r;
  339. int gy = image[x][y-1].g - image[x][0].g;
  340. int by = image[x][y-1].b - image[x][0].b;
  341.  
  342. int totX = pow(rx,2) + pow(gx,2) + pow(bx,2);
  343. int totY = pow(ry,2) + pow(gy,2) + pow(by,2);
  344.  
  345. int energy = totX + totY;
  346. return energy;
  347. }
  348. return 0;
  349. }
  350.  
  351. int loadVerticalSeam(Pixel** image, int start_col, int width, int height, int* seam) {
  352. seam[0] = start_col;
  353. int check = start_col;
  354. int totalE = energy(image, start_col, 0, width, height);
  355.  
  356.  
  357. for(int i=0; i<height-1; i++){
  358. if(check==0){
  359. int e1 = energy(image, check, i+1, width, height);
  360. int e3 = energy(image, check+1, i+1, width, height);
  361. if(e1 <= e3){
  362. seam[i+1] = check;
  363. totalE += e1;
  364. continue;
  365. }
  366. else if(e3 < e1){
  367. seam[i+1] = check+1;
  368. totalE += e3;
  369. check += 1;
  370. continue;
  371. }
  372. }
  373.  
  374. if(check==width-1){
  375. int e1 = energy(image, check, i+1, width, height);
  376. int e2 = energy(image, check-1, i+1, width, height);
  377. if(e1 <= e2){
  378. seam[i+1] = check;
  379. totalE += e1;
  380. continue;
  381. }
  382. else if(e2 < e1){
  383. seam[i+1] = check-1;
  384. totalE += e2;
  385. check -= 1;
  386. continue;
  387. }
  388. }
  389.  
  390. int e1 = energy(image, check, i+1, width, height);
  391. int e2 = energy(image, check-1, i+1, width, height);
  392. int e3 = energy(image, check+1, i+1, width, height);
  393.  
  394. if(e1 < e2 && e1 < e3){
  395. seam[i+1] = check;
  396. totalE += e1;
  397. continue;
  398. }
  399.  
  400. int smallest = min(min(e2, e1), e3);
  401. totalE += smallest;
  402.  
  403. if(smallest == e1){
  404. seam[i+1] = check;
  405. continue;
  406. }
  407. if(smallest == e3){
  408. seam[i+1] = check+1;
  409. check += 1;
  410. continue;
  411. }
  412. if(smallest == e2){
  413. seam[i+1] = check-1;
  414. check -= 1;
  415. continue;
  416. }
  417.  
  418.  
  419. }
  420.  
  421. return totalE;
  422. }
  423. int* findMinVerticalSeam(Pixel** image, int width, int height) {
  424. int* seam = createSeam(height);
  425. int small = loadVerticalSeam(image,0,width,height,seam);
  426.  
  427. for(int i = 0; i < width; i++) {
  428. int* seam2 = new int[height];
  429. int c = loadVerticalSeam(image,i,width,height,seam2);
  430. if(c < small) {
  431. small = loadVerticalSeam(image, i , width, height, seam);
  432. }
  433.  
  434. delete [] seam2;
  435. //seam2 = nullptr;
  436. }
  437. return seam;
  438. }
  439. void removeVerticalSeam(Pixel** image, int width, int height, int* verticalSeam) {
  440. for(int i = 0; i < height; i++){
  441. for(int j = verticalSeam[i]; j < (width-1); j++) {
  442. image[j][i] = image[j+1][i];
  443. }
  444. }
  445. }
  446.  
  447. int loadHorizontalSeam(Pixel** image, int start_row, int width, int height, int* seam) {
  448. return 0;
  449. }
  450. int* findMinHorizontalSeam(Pixel** image, int width, int height) {
  451. return nullptr;
  452. }
  453. void removeHorizontalSeam(Pixel** image, int width, int height, int* horizontalSeam) {
  454. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement