最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

Python cv2.imshow memory leak on macOS? - Stack Overflow

programmeradmin4浏览0评论

I believe I am witnessing a memory leak in the following Python code that calls OpenCV functions.

Can you reproduce this? Why does this happen? How can I work around it or fix it?

My environment:

  • macOS (10.12 and 10.13)
  • Python 3.8.10
  • OpenCV 3.4.18
  • NumPy 1.24.4

I've now also tested it on another machine in Python 3.9.1 with OpenCV 4.10.0 and NumPy 2.02 and experience the same behavior.

I believe it's linked to cv2.imshow. With each loop iteration (i.e. every time the image updates) the memory usage of Python increases by an amount relative to the size of the image.

Adding small = cv2.resize(img,(640,360)) and changing the imshow line to cv2.imshow('Image',small) makes the RAM increase by a much smaller amount.

By inserting a continue statement above the imshow call, and thereby skipping imshow altogether, makes the RAM stay more or less unchanged throughout the loop.

So, I guess this isolates the problem to cv2.imshow.

import cv2, numpy as np

flag = False

while True:
    img = np.zeros((2160,3840,3),np.uint8)
    if flag:
        img = cv2.circle(img, (1920,1080),128,(255,255,255),-1)
    flag = not flag
    cv2.imshow('Image',img)
    k = cv2.waitKey()
    cv2.destroyAllWindows()
    if k == 27:
        break

I believe I am witnessing a memory leak in the following Python code that calls OpenCV functions.

Can you reproduce this? Why does this happen? How can I work around it or fix it?

My environment:

  • macOS (10.12 and 10.13)
  • Python 3.8.10
  • OpenCV 3.4.18
  • NumPy 1.24.4

I've now also tested it on another machine in Python 3.9.1 with OpenCV 4.10.0 and NumPy 2.02 and experience the same behavior.

I believe it's linked to cv2.imshow. With each loop iteration (i.e. every time the image updates) the memory usage of Python increases by an amount relative to the size of the image.

Adding small = cv2.resize(img,(640,360)) and changing the imshow line to cv2.imshow('Image',small) makes the RAM increase by a much smaller amount.

By inserting a continue statement above the imshow call, and thereby skipping imshow altogether, makes the RAM stay more or less unchanged throughout the loop.

So, I guess this isolates the problem to cv2.imshow.

import cv2, numpy as np

flag = False

while True:
    img = np.zeros((2160,3840,3),np.uint8)
    if flag:
        img = cv2.circle(img, (1920,1080),128,(255,255,255),-1)
    flag = not flag
    cv2.imshow('Image',img)
    k = cv2.waitKey()
    cv2.destroyAllWindows()
    if k == 27:
        break
Share Improve this question edited 22 hours ago Christoph Rackwitz 15.5k5 gold badges39 silver badges51 bronze badges asked 2 days ago user2268171user2268171 351 silver badge6 bronze badges 7
  • does it increase without bound? how fast does it increase? can you express that in absolute terms of memory and time? -- the one answer given below ("can be fixed") is highly unlikely to fix any problem you might have, and it's unlikely to even have reproduced your issue. messing around with flag literally affects nothing that uses memory. I would strongly recommend against rewarding answers that neither repro the problem nor do anything that could even theoretically affect the problem. – Christoph Rackwitz Commented yesterday
  • thanks for investigating this further. your observations sound like the imshow call is a key piece. I agree with your suspicion that this might be related to macos, and I'd specifically suspect whatever GUI toolkit is being used by OpenCV on macos. please provide the "GUI" section of print(cv2.getBuildInformation()) – Christoph Rackwitz Commented 22 hours ago
  • 1 I also see the destroyAllWindows being called in every iteration. is this required to provoke the leak? that's a terrible thing to do in general, unless it's actually intended. – Christoph Rackwitz Commented 22 hours ago
  • 1 You found the culprit! Removing the destroyAllWindows got rid of the leak! The other stuff (flag and cv2.circle) didn't affect anything. And for the sake of it, this is what was in the GUI section of the build info: Cocoa: YES, VTK support: NO. Thank you for your help! – user2268171 Commented 21 hours ago
  • 1 I browsed the existing issues on OpenCV's github. yours might have been submitted already: github/opencv/opencv/issues/18962 and associated stackoverflow/questions/57916099/… and it sounds like OpenCV can't do anything about it (which sounds puzzling). perhaps your issue is different from that one. if you think they should work on fixing this, feel free to add your voice to the issue or open a new one. – Christoph Rackwitz Commented 20 hours ago
 |  Show 2 more comments

3 Answers 3

Reset to default 1

Is there a reason you are using old version of python CV and NP? I'm on the following versions and have no problems when I copy your snippet here:

OpenCV: 4.10.0
NumPy: 2.1.0
Python: 3.12.5

If you can update you probably should. Is there large functional difference is the major versions that would stop you from updating? If there are, maybe post the relevant code. There should be a way to adjust it to work with the new versions.

I believe it's linked to cv2.imshow. I have not been able to figure out why it's happening and how to fix it, though.

The problem can be fixed.

With Python 3.12.9 and Windows 10

  • On line 7 including boolean if not flag:
  • On line 8, decrement the x and y coordinates so you can see the circle.
  • On line 9, comment out #flag = not flag

Snippet:

import cv2, numpy as np

flag = False

while True:
    img = np.zeros((2160,3840,3),np.uint8)
    if not flag:
        img = cv2.circle(img, (640,480),128,(255,255,255),-1)
    #flag = not flag
    cv2.imshow('Image', img)
    k = cv2.waitKey(0)
    cv2.destroyAllWindows()
    if k == 27:
        break

Screenshot:

Thanks to user Christoph Rackwitz, the cause of the problem was identified as cv2.destroyAllWindows().

It seems to be present only on Mac systems and a bug report was filed, but apparently, there aren't currently any plans on fixing it.

发布评论

评论列表(0)

  1. 暂无评论