在什么情况下需要像python opencv中的重塑(-1,1,2)那样重塑点?

在什么情况下需要像python opencv中的重塑(-1,1,2)那样重塑点?,python,numpy,opencv,Python,Numpy,Opencv,我是python opencv的新手,因此我阅读了这篇文章,发现了如下示例代码: pts = np.array([[10,5],[20,30],[70,20],[50,10]], np.int32) pts = pts.reshape((-1,1,2)) cv2.polylines(img,[pts],True,(0,255,255)) convex_pts = cv2.convexHull(pts) #get a convexhull from pts,pts's shape is(4,2)

我是python opencv的新手,因此我阅读了这篇文章,发现了如下示例代码:

pts = np.array([[10,5],[20,30],[70,20],[50,10]], np.int32)
pts = pts.reshape((-1,1,2))
cv2.polylines(img,[pts],True,(0,255,255))
convex_pts = cv2.convexHull(pts) #get a convexhull from pts,pts's shape is(4,2)
print(convex_pts)       #[[[72,20]],[[20,30]],[[10,5]],[[50,10]]]
print(convex_pts.shape) #(4,1,2)
它将向您展示如何使用cv2.polylines函数绘制多边形,其中大多数都很容易理解,我很好奇的是:

pts = pts.reshape((-1,1,2)) #I understand this makes pts.shape to be (4,1,2)
我试图删除这段代码,但发现没有任何区别,它也可以正常工作。在这次整形手术之前,pts的形状是4,2,这对我来说足够直观。此外,当我编写这样的代码时:

pts = np.array([[10,5],[20,30],[70,20],[50,10]], np.int32)
pts = pts.reshape((-1,1,2))
cv2.polylines(img,[pts],True,(0,255,255))
convex_pts = cv2.convexHull(pts) #get a convexhull from pts,pts's shape is(4,2)
print(convex_pts)       #[[[72,20]],[[20,30]],[[10,5]],[[50,10]]]
print(convex_pts.shape) #(4,1,2)
在我看来,python opencv坚持将其解构并使其具有像Ex,1,2这样的形状,这对我来说很奇怪,因为当形状为x,2时,它在教程中工作得很好。有什么必要这样做的原因吗?我搜索
到处找,没有发现任何有用的东西,我是不是遗漏了什么?因此,我想知道为什么以及在什么情况下需要像这样重塑?

如果您调试第一行代码,其中说:

pts = np.array([[10,5],[20,30],[70,20],[50,10]], np.int32)
然后使用pts.shape,您将得到4,2,这意味着此时的pts有4行和2列。现在,可能接受此矩阵的函数希望以其他格式输入,在您的示例中,该格式似乎是4,1,2,这意味着4行,1列,每个元素有2个子元素。要将4,2形状转换为4,1,2形状,我们使用以下代码行:

pts = pts.reshape((-1,1,2))
上面这行的意思是,我需要一个矩阵,它的行数未知,但只有一列,每个元素有两个子元素。现在numpy在内部计算未知的大小,并自动为您创建一个矩阵。这只是一个做pts的奇特方式。重塑4,1,2

还引述:

一个形状标注可以是-1。在这种情况下,将推断该值 从数组的长度和剩余维度


这将形状从4,2更改为4,1,2,这与几个cv2函数使用的形状一致。例如,如果您想使用findContours查找轮廓,则输出轮廓的形状为x、1、y。

我们需要查看opencv文档,以了解它期望和生成的阵列形状。它似乎赋予了3个维度中的每一个都有一个特定的含义。很抱歉,我以前的描述让你误解了我的观点,所以我稍微改变了描述,现在它表达了我真正想要的。这是一个C或C++代码的接口。我们必须深入研究文档中的代码,以了解为什么x1x2行是多边形数据的预期输入/输出,以及如果得到x2行,它会做什么。这不是一个普通的numpy问题,它非常特定于opencv。这可能是一个历史工件。我浏览了一下opencv存储库。它似乎直接从C++代码生成Python代码。如果是这样,那么如果您尝试查看cv2.polylines的代码,它将作为内置代码列出,即从.so编译文件导入。如果是这样的话,那么我们非开发人员唯一能知道正在发生什么的就是实验。“更深层次的细节”隐藏在编译代码中。谢谢!很抱歉,我以前的描述让你对我的问题有点误解。pts=pts。重塑-1,1,2并不困扰我,我想知道做这种操作的原因和场景。这在很大程度上取决于你调用的方法。例如,一些API可能接受形状为5、5、3的5x5 RGB图像矩阵,这意味着5行、5列和每个元素有3个值,而一些其他库可能要求您以25、1、3或25、3、1或其他格式传递5x5 RGB图像。这在很大程度上取决于向其传递矩阵的方法/API。但在我的情况下,此操作似乎没有必要。有什么原因说明这是一种更好的方法吗?我想了解一些更深层的细节。就我有限的理解而言,这是一种更好的方法,正如ZdaR所解释的那样:对于每一行,您只有一列,它有多个子元素。说到点,这种方法对我来说更直观,因为行数表示该维度中的点数。所以,如果你想有多个平面,你仍然可以有x,n,y,其中n是平面的数量。因此,它有助于将事物从一个平面扩展到多个平面。我也是OpenCV新手,所以我可能有点错。最好进行重塑,使其与库的其他部分保持一致。从您的进一步解释中,我可以理解为什么python opencv在某种程度上坚持这样重塑,谢谢。