data_attributes.py 14 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464
  1. # main imports
  2. import numpy as np
  3. import sys
  4. # image transform imports
  5. from PIL import Image
  6. from skimage import color
  7. from sklearn.decomposition import FastICA
  8. from sklearn.decomposition import IncrementalPCA
  9. from sklearn.decomposition import TruncatedSVD
  10. from numpy.linalg import svd as lin_svd
  11. from scipy.signal import medfilt2d, wiener, cwt
  12. import pywt
  13. import cv2
  14. from ipfml.processing import transform, compression, segmentation
  15. from ipfml import utils
  16. # modules and config imports
  17. sys.path.insert(0, '') # trick to enable import of main folder module
  18. import custom_config as cfg
  19. from modules.utils import data as dt
  20. def get_svd_data(data_type, block):
  21. """
  22. Method which returns the data type expected
  23. """
  24. if data_type == 'lab':
  25. block_file_path = '/tmp/lab_img.png'
  26. block.save(block_file_path)
  27. data = transform.get_LAB_L_SVD_s(Image.open(block_file_path))
  28. if data_type == 'mscn':
  29. img_mscn_revisited = transform.rgb_to_mscn(block)
  30. # save tmp as img
  31. img_output = Image.fromarray(img_mscn_revisited.astype('uint8'), 'L')
  32. mscn_revisited_file_path = '/tmp/mscn_revisited_img.png'
  33. img_output.save(mscn_revisited_file_path)
  34. img_block = Image.open(mscn_revisited_file_path)
  35. # extract from temp image
  36. data = compression.get_SVD_s(img_block)
  37. """if data_type == 'mscn':
  38. img_gray = np.array(color.rgb2gray(np.asarray(block))*255, 'uint8')
  39. img_mscn = transform.calculate_mscn_coefficients(img_gray, 7)
  40. img_mscn_norm = transform.normalize_2D_arr(img_mscn)
  41. img_mscn_gray = np.array(img_mscn_norm*255, 'uint8')
  42. data = compression.get_SVD_s(img_mscn_gray)
  43. """
  44. if data_type == 'low_bits_6':
  45. low_bits_6 = transform.rgb_to_LAB_L_low_bits(block, 6)
  46. data = compression.get_SVD_s(low_bits_6)
  47. if data_type == 'low_bits_5':
  48. low_bits_5 = transform.rgb_to_LAB_L_low_bits(block, 5)
  49. data = compression.get_SVD_s(low_bits_5)
  50. if data_type == 'low_bits_4':
  51. low_bits_4 = transform.rgb_to_LAB_L_low_bits(block, 4)
  52. data = compression.get_SVD_s(low_bits_4)
  53. if data_type == 'low_bits_3':
  54. low_bits_3 = transform.rgb_to_LAB_L_low_bits(block, 3)
  55. data = compression.get_SVD_s(low_bits_3)
  56. if data_type == 'low_bits_2':
  57. low_bits_2 = transform.rgb_to_LAB_L_low_bits(block, 2)
  58. data = compression.get_SVD_s(low_bits_2)
  59. if data_type == 'low_bits_4_shifted_2':
  60. data = compression.get_SVD_s(transform.rgb_to_LAB_L_bits(block, (3, 6)))
  61. if data_type == 'sub_blocks_stats':
  62. block = np.asarray(block)
  63. width, height, _= block.shape
  64. sub_width, sub_height = int(width / 4), int(height / 4)
  65. sub_blocks = segmentation.divide_in_blocks(block, (sub_width, sub_height))
  66. data = []
  67. for sub_b in sub_blocks:
  68. # by default use the whole lab L canal
  69. l_svd_data = np.array(transform.get_LAB_L_SVD_s(sub_b))
  70. # get information we want from svd
  71. data.append(np.mean(l_svd_data))
  72. data.append(np.median(l_svd_data))
  73. data.append(np.percentile(l_svd_data, 25))
  74. data.append(np.percentile(l_svd_data, 75))
  75. data.append(np.var(l_svd_data))
  76. area_under_curve = utils.integral_area_trapz(l_svd_data, dx=100)
  77. data.append(area_under_curve)
  78. # convert into numpy array after computing all stats
  79. data = np.asarray(data)
  80. if data_type == 'sub_blocks_stats_reduced':
  81. block = np.asarray(block)
  82. width, height, _= block.shape
  83. sub_width, sub_height = int(width / 4), int(height / 4)
  84. sub_blocks = segmentation.divide_in_blocks(block, (sub_width, sub_height))
  85. data = []
  86. for sub_b in sub_blocks:
  87. # by default use the whole lab L canal
  88. l_svd_data = np.array(transform.get_LAB_L_SVD_s(sub_b))
  89. # get information we want from svd
  90. data.append(np.mean(l_svd_data))
  91. data.append(np.median(l_svd_data))
  92. data.append(np.percentile(l_svd_data, 25))
  93. data.append(np.percentile(l_svd_data, 75))
  94. data.append(np.var(l_svd_data))
  95. # convert into numpy array after computing all stats
  96. data = np.asarray(data)
  97. if data_type == 'sub_blocks_area':
  98. block = np.asarray(block)
  99. width, height, _= block.shape
  100. sub_width, sub_height = int(width / 8), int(height / 8)
  101. sub_blocks = segmentation.divide_in_blocks(block, (sub_width, sub_height))
  102. data = []
  103. for sub_b in sub_blocks:
  104. # by default use the whole lab L canal
  105. l_svd_data = np.array(transform.get_LAB_L_SVD_s(sub_b))
  106. area_under_curve = utils.integral_area_trapz(l_svd_data, dx=50)
  107. data.append(area_under_curve)
  108. # convert into numpy array after computing all stats
  109. data = np.asarray(data)
  110. if data_type == 'sub_blocks_area_normed':
  111. block = np.asarray(block)
  112. width, height, _= block.shape
  113. sub_width, sub_height = int(width / 8), int(height / 8)
  114. sub_blocks = segmentation.divide_in_blocks(block, (sub_width, sub_height))
  115. data = []
  116. for sub_b in sub_blocks:
  117. # by default use the whole lab L canal
  118. l_svd_data = np.array(transform.get_LAB_L_SVD_s(sub_b))
  119. l_svd_data = utils.normalize_arr(l_svd_data)
  120. area_under_curve = utils.integral_area_trapz(l_svd_data, dx=50)
  121. data.append(area_under_curve)
  122. # convert into numpy array after computing all stats
  123. data = np.asarray(data)
  124. if data_type == 'mscn_var_4':
  125. data = _get_mscn_variance(block, (100, 100))
  126. if data_type == 'mscn_var_16':
  127. data = _get_mscn_variance(block, (50, 50))
  128. if data_type == 'mscn_var_64':
  129. data = _get_mscn_variance(block, (25, 25))
  130. if data_type == 'mscn_var_16_max':
  131. data = _get_mscn_variance(block, (50, 50))
  132. data = np.asarray(data)
  133. size = int(len(data) / 4)
  134. indices = data.argsort()[-size:][::-1]
  135. data = data[indices]
  136. if data_type == 'mscn_var_64_max':
  137. data = _get_mscn_variance(block, (25, 25))
  138. data = np.asarray(data)
  139. size = int(len(data) / 4)
  140. indices = data.argsort()[-size:][::-1]
  141. data = data[indices]
  142. if data_type == 'ica_diff':
  143. current_image = transform.get_LAB_L(block)
  144. ica = FastICA(n_components=50)
  145. ica.fit(current_image)
  146. image_ica = ica.fit_transform(current_image)
  147. image_restored = ica.inverse_transform(image_ica)
  148. final_image = utils.normalize_2D_arr(image_restored)
  149. final_image = np.array(final_image * 255, 'uint8')
  150. sv_values = utils.normalize_arr(compression.get_SVD_s(current_image))
  151. ica_sv_values = utils.normalize_arr(compression.get_SVD_s(final_image))
  152. data = abs(np.array(sv_values) - np.array(ica_sv_values))
  153. if data_type == 'svd_trunc_diff':
  154. current_image = transform.get_LAB_L(block)
  155. svd = TruncatedSVD(n_components=30, n_iter=100, random_state=42)
  156. transformed_image = svd.fit_transform(current_image)
  157. restored_image = svd.inverse_transform(transformed_image)
  158. reduced_image = (current_image - restored_image)
  159. U, s, V = compression.get_SVD(reduced_image)
  160. data = s
  161. if data_type == 'ipca_diff':
  162. current_image = transform.get_LAB_L(block)
  163. transformer = IncrementalPCA(n_components=20, batch_size=25)
  164. transformed_image = transformer.fit_transform(current_image)
  165. restored_image = transformer.inverse_transform(transformed_image)
  166. reduced_image = (current_image - restored_image)
  167. U, s, V = compression.get_SVD(reduced_image)
  168. data = s
  169. if data_type == 'svd_reconstruct':
  170. reconstructed_interval = (90, 200)
  171. begin, end = reconstructed_interval
  172. lab_img = transform.get_LAB_L(block)
  173. lab_img = np.array(lab_img, 'uint8')
  174. U, s, V = lin_svd(lab_img, full_matrices=True)
  175. smat = np.zeros((end-begin, end-begin), dtype=complex)
  176. smat[:, :] = np.diag(s[begin:end])
  177. output_img = np.dot(U[:, begin:end], np.dot(smat, V[begin:end, :]))
  178. output_img = np.array(output_img, 'uint8')
  179. data = compression.get_SVD_s(output_img)
  180. if 'sv_std_filters' in data_type:
  181. # convert into lab by default to apply filters
  182. lab_img = transform.get_LAB_L(block)
  183. arr = np.array(lab_img)
  184. images = []
  185. # Apply list of filter on arr
  186. images.append(medfilt2d(arr, [3, 3]))
  187. images.append(medfilt2d(arr, [5, 5]))
  188. images.append(wiener(arr, [3, 3]))
  189. images.append(wiener(arr, [5, 5]))
  190. # By default computation of current block image
  191. s_arr = compression.get_SVD_s(arr)
  192. sv_vector = [s_arr]
  193. # for each new image apply SVD and get SV
  194. for img in images:
  195. s = compression.get_SVD_s(img)
  196. sv_vector.append(s)
  197. sv_array = np.array(sv_vector)
  198. _, len = sv_array.shape
  199. sv_std = []
  200. # normalize each SV vectors and compute standard deviation for each sub vectors
  201. for i in range(len):
  202. sv_array[:, i] = utils.normalize_arr(sv_array[:, i])
  203. sv_std.append(np.std(sv_array[:, i]))
  204. indices = []
  205. if 'lowest' in data_type:
  206. indices = utils.get_indices_of_lowest_values(sv_std, 200)
  207. if 'highest' in data_type:
  208. indices = utils.get_indices_of_highest_values(sv_std, 200)
  209. # data are arranged following std trend computed
  210. data = s_arr[indices]
  211. # with the use of wavelet
  212. if 'wave_sv_std_filters' in data_type:
  213. # convert into lab by default to apply filters
  214. lab_img = transform.get_LAB_L(block)
  215. arr = np.array(lab_img)
  216. images = []
  217. # Apply list of filter on arr
  218. images.append(medfilt2d(arr, [3, 3]))
  219. images.append(medfilt2d(arr, [5, 5]))
  220. images.append(medfilt2d(arr, [7, 7]))
  221. images.append(wiener(arr, [3, 3]))
  222. images.append(wiener(arr, [4, 4]))
  223. images.append(wiener(arr, [5, 5]))
  224. images.append(w2d(arr, 'haar', 2))
  225. images.append(w2d(arr, 'haar', 3))
  226. images.append(w2d(arr, 'haar', 4))
  227. # By default computation of current block image
  228. s_arr = compression.get_SVD_s(arr)
  229. sv_vector = [s_arr]
  230. # for each new image apply SVD and get SV
  231. for img in images:
  232. s = compression.get_SVD_s(img)
  233. sv_vector.append(s)
  234. sv_array = np.array(sv_vector)
  235. _, len = sv_array.shape
  236. sv_std = []
  237. # normalize each SV vectors and compute standard deviation for each sub vectors
  238. for i in range(len):
  239. sv_array[:, i] = utils.normalize_arr(sv_array[:, i])
  240. sv_std.append(np.std(sv_array[:, i]))
  241. indices = []
  242. if 'lowest' in data_type:
  243. indices = utils.get_indices_of_lowest_values(sv_std, 200)
  244. if 'highest' in data_type:
  245. indices = utils.get_indices_of_highest_values(sv_std, 200)
  246. # data are arranged following std trend computed
  247. data = s_arr[indices]
  248. if 'filters_statistics' in data_type:
  249. img_width, img_height = 200, 200
  250. lab_img = transform.get_LAB_L(block)
  251. arr = np.array(lab_img)
  252. # compute all filters statistics
  253. def get_stats(arr, I_filter):
  254. e1 = np.abs(arr - I_filter)
  255. L = np.array(e1)
  256. mu0 = np.mean(L)
  257. A = L - mu0
  258. H = A * A
  259. E = np.sum(H) / (img_width * img_height)
  260. P = np.sqrt(E)
  261. return mu0, P
  262. stats = []
  263. kernel = np.ones((3,3),np.float32)/9
  264. stats.append(get_stats(arr, cv2.filter2D(arr,-1,kernel)))
  265. kernel = np.ones((5,5),np.float32)/25
  266. stats.append(get_stats(arr, cv2.filter2D(arr,-1,kernel)))
  267. stats.append(get_stats(arr, cv2.GaussianBlur(arr, (3, 3), 0.5)))
  268. stats.append(get_stats(arr, cv2.GaussianBlur(arr, (3, 3), 1)))
  269. stats.append(get_stats(arr, cv2.GaussianBlur(arr, (3, 3), 1.5)))
  270. stats.append(get_stats(arr, cv2.GaussianBlur(arr, (5, 5), 0.5)))
  271. stats.append(get_stats(arr, cv2.GaussianBlur(arr, (5, 5), 1)))
  272. stats.append(get_stats(arr, cv2.GaussianBlur(arr, (5, 5), 1.5)))
  273. stats.append(get_stats(arr, medfilt2d(arr, [3, 3])))
  274. stats.append(get_stats(arr, medfilt2d(arr, [5, 5])))
  275. stats.append(get_stats(arr, wiener(arr, [3, 3])))
  276. stats.append(get_stats(arr, wiener(arr, [5, 5])))
  277. wave = w2d(arr, 'db1', 2)
  278. stats.append(get_stats(arr, np.array(wave, 'float64')))
  279. data = []
  280. for stat in stats:
  281. data.append(stat[0])
  282. for stat in stats:
  283. data.append(stat[1])
  284. data = np.array(data)
  285. return data
  286. def w2d(arr, mode='haar', level=1):
  287. #convert to float
  288. imArray = arr
  289. np.divide(imArray, 255)
  290. # compute coefficients
  291. coeffs=pywt.wavedec2(imArray, mode, level=level)
  292. #Process Coefficients
  293. coeffs_H=list(coeffs)
  294. coeffs_H[0] *= 0
  295. # reconstruction
  296. imArray_H = pywt.waverec2(coeffs_H, mode)
  297. imArray_H *= 255
  298. imArray_H = np.uint8(imArray_H)
  299. return imArray_H
  300. def _get_mscn_variance(block, sub_block_size=(50, 50)):
  301. blocks = segmentation.divide_in_blocks(block, sub_block_size)
  302. data = []
  303. for block in blocks:
  304. mscn_coefficients = transform.get_mscn_coefficients(block)
  305. flat_coeff = mscn_coefficients.flatten()
  306. data.append(np.var(flat_coeff))
  307. return np.sort(data)