OpenCV python不显示python转换为OpenCV关键点格式的Cuda SIFT关键点

问题描述

我们在ExtractSift函数周围使用了pybind11编写了一个小的python包装器,看来工作正常。

这是它的样子:

ID | Night_Shift | Day_Shift | Weekend_Shift | Morning_Shift | New_Col
    3       True         False         True          True        True
    1       False        False         False          False       False
    2       True         False         False          False       True

这种用法可以正确绘制关键点

std::vector<SiftPoint> extractSIFT(char* filename)
{
    int devNum = 0,imgSet = 0;
    cv::Mat img;
    cv::imread(filename,0).convertTo(img,CV_32FC1);
    unsigned int w = img.cols;
    unsigned int h = img.rows;

    InitCuda(devNum);
    Cudaimage img1;
    img1.Allocate(w,h,iAlignUp(w,128),false,NULL,(float*)img.data);
    img1.Download();
    
    SiftData siftData1;
    float initBlur = 1.0f;
    float thresh = (imgSet ? 4.5f : 3.0f);
    InitSiftData(siftData1,32768,true,true); 
    float *memoryTmp = AllocSiftTempMemory(w,5,false);
    ExtractSift(siftData1,img1,initBlur,thresh,0.0f,memoryTmp);
    FreeSiftTempMemory(memoryTmp);
    return std::vector<SiftPoint>(siftData1.h_data,siftData1.h_data + siftData1.numPts);
}

PYBIND11_MODULE(pycusift,m) {
    m.doc() = "SIFT feature extractor with CUDA"; // optional module docstring

    m.def("extractSIFT",&extractSIFT,"function to extract SIFT features from image");
    py::class_<SiftPoint>(m,"SiftPoint")
    .def(py::init<>())
    .def_readwrite("xpos",&SiftPoint::xpos)
    .def_readwrite("ypos",&SiftPoint::ypos)
    .def_readwrite("sharpness",&SiftPoint::sharpness)
    .def_readwrite("edgeness",&SiftPoint::edgeness)
    .def_readwrite("ambiguity",&SiftPoint::ambiguity)
    .def_readwrite("orientation",&SiftPoint::orientation)
    .def_readwrite("score",&SiftPoint::score)
    .def_readwrite("match",&SiftPoint::match)
    .def_readwrite("match_xpos",&SiftPoint::match_xpos)
    .def_readwrite("match_ypos",&SiftPoint::match_ypos)
    .def_readwrite("match_error",&SiftPoint::match_error)
    .def_readwrite("subsampling",&SiftPoint::ypos)
    .def_readwrite("scale",&SiftPoint::scale)
    .def("getempty",&SiftPoint::getempty)
    .def("getdata",&SiftPoint::getdata);
}

以下代码尝试使用opencv显示关键点但未显示任何关键点,我认为这可能是浮动类型转换问题


import pycusift

a = pycusift.extractSIFT("001.tiff")
x = [i.xpos for i in a]
y = [i.ypos for i in a]
import matplotlib.pyplot as plt
import cv2
plt.imshow(cv2.imread("001.tiff"))
plt.scatter(x,y)
plt.show() 

我必须指出,我认为knn描述符匹配正在起作用,因为它正在生成匹配项

以下是打印语句的输出

(431.0779724121094,982.3478393554688)

224.15390014648438

解决方法

我找到了解决方案,不得不将kp = cv.keypoint()放入for循环中:

def extract_sift_keypoints(impath,kpts):
    im = cv.imread(impath,cv.IMREAD_COLOR)
    kp1 = []
    desc1 = (np.array([k.getdata() for k in kpts],dtype=np.float32))
    

    for k in kpts :
        kp = cv.KeyPoint()
        kp.pt = (k.xpos,k.ypos)
        kp.angle = k.orientation
        kp.size = k.scale
        kp1.append(kp)

    pts = np.array([k.pt for k in kp1],dtype=np.float32)
    ors = np.array([k.angle for k in kp1],dtype=np.float32)
    scs = np.array([k.size for k in kp1],dtype=np.float32) 

    return pts,ors,scs,desc1,im,kp1