我尝试使用openCV从图像中隔离文本,然后将其发送到tesseract4引擎以最大化结果。
我找到了这个interesting post,我决定复制源代码并尝试使用mysdelf
但是我遇到first call to OpenCV
的问题重现:
只需复制gist中的代码
启动命令script.py /path/to/image.jpg
我遇到问题:
Required argument 'threshold2' (pos 4) not found
您是否知道这意味着什么? 我是一个javascript,java和bash脚本开发人员,但不是python ...
简单版:
import glob
import os
import random
import sys
import random
import math
import json
from collections import defaultdict
import cv2
from PIL import Image, ImageDraw
import numpy as np
from scipy.ndimage.filters import rank_filter
if __name__ == '__main__':
if len(sys.argv) == 2 and '*' in sys.argv[1]:
files = glob.glob(sys.argv[1])
random.shuffle(files)
else:
files = sys.argv[1:]
for path in files:
out_path = path.replace('.jpg', '.crop.png')
if os.path.exists(out_path): continue
orig_im = Image.open(path)
edges = cv2.Canny(np.asarray(orig_im), 100, 200)
提前感谢您的帮助
答案 0 :(得分:3)
编辑:好吧所以这个答案显然是错误的,因为我试图将自己的16位int图像发送到函数中并且无法重现结果。
编辑2:因此我可以使用以下内容重现错误:
from PIL import Image
import numpy as np
import cv2
orig_im = Image.open('opencv-logo2.png')
threshold1 = 50
threshold2 = 150
edges = cv2.Canny(orig_im, 50, 100)
TypeError:未找到必需参数'threshold2'(pos 4)
因此,如果图像不强制转换为数组,即传入Image
类,则会收到错误消息。 PIL Image
类是一个除了与之关联的图像数据之外还有很多东西的类,因此需要转换为np.array
才能传递给函数。但如果它被正确演员,那么一切都会为我膨胀。
在与Dan Mašek的聊天中,我的想法有点不正确。确实,较新的Canny()
方法需要16位图像,但绑定不会查看实际的numpy dtype
,以查看决定使用哪个函数调用的位深度。另外,如果您尝试实际发送uint16
图片,则会收到其他错误:
edges = cv2.Canny(np.array([[0, 1234], [1234, 2345]], dtype=np.uint16), 50, 100)
错误:(-215)深度== CV_8U函数Canny
所以我最初给出的答案(下面)并不是罪魁祸首。也许你不小心删除了np.array()
的{{1}}投射并得到了错误,或,还有一些奇怪的事情发生。
原始(错误)回答
在OpenCV 3.2.0中,引入了orig_im
的新方法,允许用户指定自己的渐变图像。在原始实现中,Canny()
会使用Canny()
运算符来计算渐变,但现在您可以计算出Sobel()
衍生物并将那些传递给{{ 1}}而不是。所以这很酷。但是这与你的问题有什么关系?
Scharr()
方法已超载。它根据您发送的参数决定要使用哪个函数。Canny()
的原始调用带有所需的参数,如
Canny()
但是新的重载方法看起来像
Canny()
现在,您的错误消息中有一个提示:
未找到必需参数'threshold2'(位置4)
这些电话中的哪一个在第4位有cv2.Canny(image, threshold1, threshold2)
?更新的方法调用!那么,如果你只通过了三个args,为什么要被召唤呢?请注意,如果您使用的是cv2.Canny(grad_x, grad_y, threshold1, threshold2)
图片,则会收到错误,但如果您使用的是threshold2
图片,则会收到错误。那么还有什么让它假设你正在使用新的呼叫?
如果您选中OpenCV 3.3.0 Canny()
docs,您会看到原始PIL
调用需要第一个位置参数的 8位输入图像,而新{{ {1}}调用需要输入图像的 16位x导数(CV_16SC1或CV_16SC3)作为第一个位置参数。
将两个和两个放在一起,PIL给你一个16位输入图像,所以OpenCV认为你试图调用新方法。
因此,如果您想继续使用PIL,此处的解决方案是将图像转换为8位表示。 numpy
首先需要运行单通道(即灰度)图像。因此,您需要先确保Canny()
是单通道,然后对其进行缩放并更改numpy Canny()
。我相信PIL会将灰度图像作为单通道读取(默认情况下,OpenCV会将所有图像读为三通道,除非您另有说明)。
如果图像是16位,则numpy转换很容易:
Canny()
这假定image
是一个numpy数组,因此您需要先使用dtype
或img = (img/256).astype('uint8')
将PIL图像转换为img
。
然后您应该能够使用原始函数调用运行ndarray
。
答案 1 :(得分:1)
问题来自于使用的接口和openCV版本之间的不兼容性。
我使用的是openCV 3.3,所以调用它的正确方法是:
UIColor(red: CGFloat(0.5), green: CGFloat(0.5), blue: CGFloat(1.0), alpha: CGFloat(1.0))