rendrom / rosreestr2coord

Вычисление координат участка по кадастровому номеру с сайта https://pkk.rosreestr.ru
MIT License
167 stars 79 forks source link

Во время получения геометрии удаляем неиспользуемые промежуточные изображения #60

Closed 2joy closed 2 years ago

2joy commented 2 years ago

Когда имеем дело с кадастровыми участками большой площади, метод get_image_xy_corner потребляет много памяти. Вот результат профилирования при работе с участком 47:26:0000000:39343:

Line #    Mem usage    Increment  Occurrences   Line Contents
=============================================================
   340     33.3 MiB     33.3 MiB           1       @profile
   341                                             def get_image_xy_corner(self):
   342                                                 """get сartesian coordinates from raster"""
   343     49.2 MiB     15.9 MiB           1           import cv2
   344     49.2 MiB      0.0 MiB           1           import numpy
   345                                         
   346     49.2 MiB      0.0 MiB           1           if not self.image_path:
   347                                                     return False
   348     49.2 MiB      0.0 MiB           1           image_xy_corners = []
   349                                         
   350     49.2 MiB      0.0 MiB           1           try:
   351                                                     # img = cv2.imread(self.image_path, cv2.IMREAD_GRAYSCALE)
   352     49.2 MiB      0.0 MiB           1               stream = open(self.image_path, "rb")
   353     50.4 MiB      1.2 MiB           1               bytes = bytearray(stream.read())
   354     50.4 MiB      0.0 MiB           1               numpyarray = numpy.asarray(bytes, dtype=numpy.uint8)
   355    819.1 MiB    768.7 MiB           1               img = cv2.imdecode(numpyarray, cv2.IMREAD_GRAYSCALE)
   356   1587.1 MiB    768.1 MiB           1               imagem = 255 - img
   357   2356.0 MiB    768.9 MiB           1               ret, thresh = cv2.threshold(imagem, 10, 128, cv2.THRESH_BINARY)
   ...  # Далее потребление практически не растёт

Очевидно, что можем высвободить значительное количество памяти за счёт удаления промежуточных изображений, которые далее не используются. Результат профилирование после внесения правок:

Line #    Mem usage    Increment  Occurrences   Line Contents
=============================================================
   ...
   355    818.2 MiB    768.7 MiB           1               img = cv2.imdecode(numpyarray, cv2.IMREAD_GRAYSCALE)
   356   1586.2 MiB    768.1 MiB           1               imagem = 255 - img
   357    818.2 MiB   -768.0 MiB           1               del img
   358   1587.1 MiB    768.9 MiB           1               ret, thresh = cv2.threshold(imagem, 10, 128, cv2.THRESH_BINARY)
   359    819.1 MiB   -768.0 MiB           1               del imagem
   360    819.1 MiB      0.0 MiB           1               try:
   361    820.8 MiB      1.6 MiB           2                   contours, hierarchy = cv2.findContours(
   362    819.1 MiB      0.0 MiB           1                       thresh, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE
   363                                                         )
   364                                                     except Exception:
   365                                                         im2, contours, hierarchy = cv2.findContours(
   366                                                             thresh, cv2.RETR_CCOMP, cv2.CHAIN_APPROX_SIMPLE
   367                                                         )
   368     52.8 MiB   -768.0 MiB           1               del thresh
   ...
rendrom commented 2 years ago

Круто! Спасибо