opencv.imshow 会导致 jupyter notebook 崩溃
Posted
技术标签:
【中文标题】opencv.imshow 会导致 jupyter notebook 崩溃【英文标题】:opencv.imshow will cause jupyter notebook crash 【发布时间】:2018-02-24 10:42:06 【问题描述】:我在 google 或 *** 上查看了其他问题,他们说的是在脚本中运行 cv2.imshow,但我的代码在 jupyter notebook 中运行。
这是我的配置:
ubuntu 16.4x64
python 3.5
opencv 3.1.0
我启动了一个 jupyter 笔记本:这是我把它放在笔记本上的代码:
%pylab notebook
import cv2
cvim2disp = cv2.imread('data/home.jpg')
cv2.imshow('HelloWorld', cvim2disp)
cv2.waitKey() #image will not show until this is called
cv2.destroyWindow('HelloWorld') #make sure window closes cleanly
当我执行这些代码时。图像会显示在弹出窗口中,但我无法通过单击右上角的 x 来关闭此窗口,稍后系统会提示我该窗口没有响应,它会给我两个选择:"等待”,“退出”。如果我点击等待,那么稍后它会显示相同的提示,如果我点击'fore quit',那么jupyter notebook内核就会死掉,我必须重新开始。
我google了一下,很多解决方案建议我应该添加这段代码
cv2.startWindowThread()
在imshow
之前,但情况变得更糟,内核永远挂起!。
任何人都知道发生了什么。
这是我的错误图片:
【问题讨论】:
cv.imshow
在像 Jupyter 这样的客户端/服务器环境中并没有什么意义。您想要将图像显示为笔记本的一部分(在客户端)的东西,而不是在服务器端运行 GUI 窗口——当客户端和服务器在同一台机器上时,这可能有点“工作”,但是就是这样。 |您已经使用了 matplotlib 中的 imshow
函数(不像您认为的那样 numpy),所以请坚持使用(请记住,它使用 RGB 而不是 BGR 颜色平面的顺序)。
你找到解决方案了吗,我也遇到了同样的问题,我用过很多次opencv,所以不是waitkey问题。它只发生在程序完成之前的最后一个 imshow() ,因此您显示和销毁窗口,直到您需要关闭最后一个窗口(即使它与之前的所有窗口相同,例如循环中的最后一次迭代)。
【参考方案1】:
%matplotlib inline
from matplotlib import pyplot as plt
img = cv2.imread(valid_img_paths[1])
plt.imshow(cv2.cvtColor(img, cv2.COLOR_BGR2RGB))
plt.show()
【讨论】:
这是一个很好的答案,将 Ritu dhoot 和 mannygover 的答案结合在一起。虽然可以这样做,但当您将其他人的部分答案复制到您的答案时,请引用您的来源。【参考方案2】:如果您在 google collab 中遇到问题,您可以使用此补丁
from google.colab.patches import cv2_imshow
cv2_imshow(img)
【讨论】:
【参考方案3】:image = cv2.imread(file_path)
while True:
# Press 'q' for exit
exit_key = ord('q')
if cv2.waitKey(exit_key) & 255 == exit_key:
cv2.destroyAllWindows()
break
cv2.imshow('Image_title', image)
【讨论】:
虽然此代码可能会为问题提供解决方案,但最好添加有关其工作原理/方式的上下文。这可以帮助未来的用户学习并将这些知识应用到他们自己的代码中。在解释代码时,您也可能会以赞成票的形式从用户那里获得积极的反馈。 除了@borchvm 所说的之外,它在用大量现有答案回答旧线程时也很有用,以解释为什么你的方法是其他建议的一个很好的替代方案。这样,当人们浏览答案时,他们可以快速了解为什么他们应该考虑这种方法而不是其他方法。【参考方案4】:这将帮助您了解正在发生的事情:
import cv2
cvim2disp = cv2.imread('data/home.jpg')
cv2.imshow('HelloWorld', cvim2disp)
cv2.waitKey(0)
cv2.destroyWindow('HelloWorld')
waitKey(0)
方法正在无限等待输入。当您看到相应图像的一帧时,请不要尝试使用右上角的关闭来关闭图像。
改为按某个键。 waitkey
方法会将其作为输入并返回一个值。此外,您还可以检查按下了哪个键来关闭框架。
另外waitKey(33)
将保持框架活动 33 毫秒,然后自动关闭它。
destroyWindow()
将销毁当前帧(如果存在)。
destroyAllWindows()
将销毁当前存在的所有帧。
这会解决的。
【讨论】:
不确定waitkey是这个问题的原因,我也遇到了。 这就是我的情况。此处发布的matplotlib
答案似乎只是解决方法,而不是实际解释它为什么崩溃/冻结。
添加等待键和销毁窗口没有帮助。笔记本仍然崩溃
这在 jupyter notebook 中不起作用仍然冻结。【参考方案5】:
我遇到了类似的问题,无法在 Jupyter Notebook 中使用 cv2.imshow()
找到一个好的解决方案。我跟着this *** answer,只是用matplotlib来显示图片。
import matplotlib.pyplot as plt
# load image using cv2....and do processing.
plt.imshow(cv2.cvtColor(image, cv2.COLOR_BGR2RGB))
# as opencv loads in BGR format by default, we want to show it in RGB.
plt.show()
【讨论】:
cv2.BGR2RGB 现在称为 cv2.COLOR_BGR2RGB 我在尝试循环显示太多大图时遇到了同样的问题。它发生在plt.show()
和简单的dislay(image)
【参考方案6】:
从 Jupyter 打开的新窗口使用与笔记本相同的内核。只需将其添加到代码中,它就可以正常工作。
cv2.waitKey(0)
cv2.destroyAllWindows()
【讨论】:
欢迎来到 SO!请您编辑您的帖子并简要说明您在做什么?【参考方案7】:以下代码在 Jupyter 中可以正常显示一张图像
%matplotlib inline
import cv2
from matplotlib import pyplot as plt
cap = cv2.VideoCapture(videoFName)
ret, image = cap.read()
image=cv2.resize(image,None,fx=0.25,fy=0.25,interpolation=cv2.INTER_AREA)
plt.imshow(image)
plt.show()
如果您想在单独的窗口中显示视频而不是图像,请使用以下代码:
import cv2
cap = cv2.VideoCapture(videoFName)
while cap.isOpened():
ret, image = cap.read()
image=cv2.resize(image,None,fx=0.25,fy=0.25,interpolation=cv2.INTER_AREA)
cv2.imshow('image',image)
k = cv2.waitKey(30) & 0xff # press ESC to exit
if k == 27 or cv2.getWindowProperty('image', 0)<0:
break
cv2.destroyAllWindows()
cap.release()
确保窗口名称匹配,否则将无法正常工作。在这种情况下,我使用“图像”作为窗口名称。
【讨论】:
【参考方案8】:%matplotlib inline
#The line above is necesary to show Matplotlib's plots inside a Jupyter Notebook
import cv2
from matplotlib import pyplot as plt
#Import image
image = cv2.imread("input_path")
#Show the image with matplotlib
plt.imshow(image)
plt.show()
【讨论】:
您能否在答案中添加更多细节? 它以内联模式使用 matplotlib Python 库(因此您可以在 Notebook 上看到它)。然后,它使用 cv2 加载图像,然后使用 matplotlib 显示图形 这不是一个答案,它展示了如何使用 matplotlib 而不是 opencv。 matplotlib 是一个很好的解决方法,因为它似乎无法在 jupyter 笔记本中内联显示 opencv 图像 这会产生不正确的图像输出,因为 OpenCV 使用 BGR 数组而不是 RGB。在使用 plt 之前,我们需要使用cv2.cvtColor(image, cv2.COLOR_BGR2RGB)
将 BGR 转换为 RGB。【参考方案9】:
我不确定您是否可以从 Jupyter Notebook 打开一个窗口。 cv2.imshow 需要一个在 Jupyter 中不起作用的 waitKey。
这是我所做的(使用 OpenCV 3.3):
from IPython.display import display, html
import cv2
import base64
def imshow(name, imageArray):
_, png = cv2.imencode('.png', imageArray)
encoded = base64.b64encode(png)
return HTML(data='''<img src="data:image/png;base64, 1"/>'''.format(name, encoded.decode('ascii')))
img = cv2.imread('./media/baboon.jpg',cv2.IMREAD_COLOR)
imshow('baboon', img)
如果你不需要使用 cv2,只需:
from IPython.display import Image
Image('./media/baboon.jpg')
【讨论】:
【参考方案10】:API documentation for cv2.waitKey() 注释如下:
该函数是 HighGUI 中唯一可以获取和处理事件的方法,因此需要定期调用它以进行正常的事件处理,除非在负责事件处理的环境中使用 HighGUI。
所以也许在无限循环中调用函数会使窗口响应?我没有对此进行测试,但也许您想尝试以下方法:
import cv2
cvim2disp = cv2.imread('data/home.jpg')
cv2.imshow('img', cvim2disp)
while(True):
k = cv2.waitKey(33)
if k == -1: # if no key was pressed, -1 is returned
continue
else:
break
cv2.destroyWindow('img')
【讨论】:
你也可以在最后使用cv2.destroyAllWindows()
来销毁所有窗口。以上是关于opencv.imshow 会导致 jupyter notebook 崩溃的主要内容,如果未能解决你的问题,请参考以下文章
OpenCV - imshow()在等待来自命令窗口的输入时没有响应
带有 Python 3 的 opencv3,imshow() 不显示图像