Python 如何以一致的方式从左到右、从上到下对轮廓进行排序

Python 如何以一致的方式从左到右、从上到下对轮廓进行排序,python,opencv,computer-vision,Python,Opencv,Computer Vision,我正在研究一个从图像中提取矩形框并按顺序排序的问题。我尝试的代码是: import cv2 import matplotlib.pyplot as plt # Load image, grayscale, adaptive threshold image = cv2.imread('3.jpg') result = image.copy() gray = cv2.cvtColor(image,cv2.COLOR_BGR2GRAY) thresh = cv2.adaptiveThreshold(g

我正在研究一个从图像中提取矩形框并按顺序排序的问题。我尝试的代码是:

import cv2
import matplotlib.pyplot as plt
# Load image, grayscale, adaptive threshold
image = cv2.imread('3.jpg')
result = image.copy()
gray = cv2.cvtColor(image,cv2.COLOR_BGR2GRAY)
thresh = cv2.adaptiveThreshold(gray,255,cv2.ADAPTIVE_THRESH_GAUSSIAN_C, cv2.THRESH_BINARY_INV,51,9)

# Fill rectangular contours
cnts = cv2.findContours(thresh, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
cnts = cnts[0] if len(cnts) == 2 else cnts[1]
for c in cnts:
    cv2.drawContours(thresh, [c], -1, (255,255,255), -1)

# Morph open
kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (9,9))
opening = cv2.morphologyEx(thresh, cv2.MORPH_OPEN, kernel, iterations=4)
plt.imshow(thresh)

# Draw rectangles
cnts = cv2.findContours(opening, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
cnts = cnts[0] if len(cnts) == 2 else cnts[1]
cnts = sorted(cnts, key=lambda x: [cv2.boundingRect(x)[1], cv2.boundingRect(x)[0]])
# cnts = sorted(cnts, key=lambda ctr: cv2.boundingRect(ctr)[0] + cv2.boundingRect(ctr)[1] * image.shape[1], reverse=True)
i = 0
for c in cnts:
    area = cv2.contourArea(c)
#     print("Area:", area)
    x,y,w,h = cv2.boundingRect(c)
    
#     cv2.rectangle(image, (x+8, y+8), (x + w-8, y + h-8), (36,255,12), 1)
    roi = image[y:y+h, x:x+w]
    cv2.imwrite('{}.jpg'.format(i), roi)
    i += 1


cv2.imwrite('output_image.jpg', image)
cv2.imshow('thresh', thresh)
cv2.imshow('opening', opening)
cv2.imshow('image', image)
cv2.waitKey()
cv2.destroyAllWindows()
用于检测和提取轮廓的图像:。 我想按顺序1-2-3-4-5-6-7------32提取包含数字的框。上面的代码以随机顺序提取框,有时从左到右,有时从右到左

[已编辑] 按4-3-2-18-7-6-5顺序生成轮廓的图像。。。
按1-2-3-4 5-6-7-8顺序生成轮廓的图像。。。
是纸张的方向或旋转决定了是否只需检查轮廓边界框的
(x,y)
坐标就足够了

所以,我只会坚持一些好的比较方法,例如。不幸的是,在Python3中完全删除了在
sorted
中使用。但是,我们可以使用
functools
模块中的
cmp\u to_key
,将该功能映射到适当的
key
函数

现在,首先,让我们创建比较方法:

def等高线_排序(a、b):
br_a=cv2.boundingRect(a)
br_b=cv2.boundingRect(b)

如果abs(br_a[1]-br_b[1]),这是否回答了您的问题?它起了部分作用。我测试了6张图像,4张图像按顺序返回轮廓,但2张图像的轮廓是按顺序4-3-2-1..8-7-6-5..12-11-10-9…..请将两张成功的和两张错误的图像添加到您的问题中。我已编辑了问题。请参阅