Python 使用cython包装错误级别分析算法的opencv实现

Python 使用cython包装错误级别分析算法的opencv实现,python,cython,wrapper,Python,Cython,Wrapper,我已经用c++实现了一个错误级别分析算法(opencv版本2.4),我想用cython为它构建一个python包装器。 我已经阅读了Cython的C++文档的一些部分,但它对我没有帮助,而且我没有发现任何额外的信息来实现包装器在线。 如果有人能指导我,帮助我解决这个问题,那就太好了 这是我要为其构建pyhton包装的代码: #include <opencv2/highgui/highgui.hpp> #include <iostream> #include <vec

我已经用c++实现了一个错误级别分析算法(opencv版本2.4),我想用cython为它构建一个python包装器。 我已经阅读了Cython的C++文档的一些部分,但它对我没有帮助,而且我没有发现任何额外的信息来实现包装器在线。 如果有人能指导我,帮助我解决这个问题,那就太好了

这是我要为其构建pyhton包装的代码:

#include <opencv2/highgui/highgui.hpp>
#include <iostream>
#include <vector> 

// Control
int scale = 15,
quality = 75;

// Image containers
cv::Mat input_image,
compressed_image;

void processImage(int, void*)
{

// Setting up parameters and JPEG compression
std::vector<int> parameters;
parameters.push_back(CV_IMWRITE_JPEG_QUALITY);
parameters.push_back(quality);
cv::imwrite("lena.jpeg", input_image, parameters);

// Reading temp image from the disk
compressed_image = cv::imread("lena.jpeg");

if (compressed_image.empty())
{
  std::cout << "> Error loading temp image" << std::endl;
  exit(EXIT_FAILURE);
}

cv::Mat output_image = cv::Mat::zeros(input_image.size(), CV_8UC3);

// Compare values through matrices
for (int row = 0; row < input_image.rows; ++row)
{
 const uchar* ptr_input = input_image.ptr<uchar>(row);
 const uchar* ptr_compressed = compressed_image.ptr<uchar>(row);
 uchar* ptr_out = output_image.ptr<uchar>(row);

    for (int column = 0; column < input_image.cols; column++)
    {
        // Calc abs diff for each color channel multiplying by a scale factor
        ptr_out[0] = abs(ptr_input[0] - ptr_compressed[0]) * scale;
        ptr_out[1] = abs(ptr_input[1] - ptr_compressed[1]) * scale;
        ptr_out[2] = abs(ptr_input[2] - ptr_compressed[2]) * scale;

        ptr_input += 3;
        ptr_compressed += 3;
        ptr_out += 3;
    }
}

// Shows processed image
cv::imshow("Error Level Analysis", output_image);
} 

int main (int argc, char* argv[])
{
// Verifica se o número de parâmetros necessário foi informado
if (argc < 2)
{
 std::cout << "> You need to provide an image as parameter" << std::endl;
 return EXIT_FAILURE;
}

// Read the image
input_image = cv::imread(argv[1]);

// Check image load
if (input_image.empty())
{
  std::cout << "> Error loading input image" << std::endl;
  return EXIT_FAILURE;
}

// Set up window and trackbar
cv::namedWindow("Error Level Analysis", CV_WINDOW_AUTOSIZE);
cv::imshow("Error Level Analysis", input_image);
cv::createTrackbar("Scale", "Error Level Analysis", &scale, 100,   processImage);
cv::createTrackbar("Quality", "Error Level Analysis", &quality, 100, processImage);

// Press 'q' to quit
while (char(cv::waitKey(0)) != 'q') {};

return EXIT_SUCCESS;
} 
#包括
#包括
#包括
//控制
整数比例=15,
质量=75;
//图像容器
cv::Mat输入_图像,
压缩图像;
void processImage(int,void*)
{
//设置参数和JPEG压缩
std::向量参数;
参数。推回(CV\u IMWRITE\u JPEG\u质量);
参数。推回(质量);
cv::imwrite(“lena.jpeg”,输入图像,参数);
//从磁盘读取临时映像
压缩图像=cv::imread(“lena.jpeg”);
if(压缩的_image.empty())
{

std::cout这并不清楚您希望通过它实现什么,但是让函数从Cython调用非常容易。首先对
main
进行一些小的更改-它需要重命名,以便不再作为程序的主函数,并且因为您只使用第二个命令行参数作为文件名您应该将其更改为:

void some_function(char* filename) {
    // Read the image
    input_image = cv::imread(filename);
    // everything else the same
}

创建Cython包装器>代码> CythBase.pyx。这里有两个部分。首先,您需要告诉Cython关于两个C++函数(<代码> CDEF ExtEng/<代码>)。第二,您需要编写一个小的包装器函数,可以从Python调用这些:

cdef extern from "ela.hpp":
    # you'll need to create ela.hpp with declarations for your two functions
    void processImage(int, void*)
    void some_function(char* filename)

# and Python wrappers
def processImagePy():
   # since the parameters are ignored in C++ we can pass anything
   processImage(0,NULL)

def some_functionPy(filename):
   # automatic conversion from string to char*
   some_function(filename)
使用此模块,您将能够调用
processImagePy
一些函数py


要将其编译成Python模块,您需要编写一个setup.py文件。您的源文件将是
cy_wrap.pyx
ela.cpp
。您可能需要链接到OpenCV库。您需要

我认为您需要详细考虑您想要什么:根据您的github,您有一个函数忽略其参数,但不返回任何内容-这看起来并不是什么意思你也有一个主程序,它接受一些文件名作为命令行参数,并调用opencv——这也不是用Cython包装的好方法。你还把代码放到了场外,所以这不是一个独立的问题。最后,已经有了一个Python的opencv包装器了?为什么不使用它呢?先生,使用cython是提供给我的任务的一部分,也是完成任务的必要条件。我是cython的新手,因此如果您能指导我使用cython包装上述代码,那将是非常棒的,例如,包装和其他相关内容将涉及哪些类。谢谢。Thanx非常感谢,我能够构建使用cython为我的程序初始化,但在测试期间,我得到以下错误:ImportError:/home/shryah/Desktop/New/ela_c.so:未定义的符号:zn2Cv14 CreateTrackBarerkNST7_cx1112基本_stringIcSt11char_traitsIceees7_piipfvipVes9,看起来像OpenCV的一部分我可能需要更改
库中的内容。虽然我从未使用过OpenCV,因此我无法真正帮助Thanx先生,谢谢您的帮助,但我认为我无法将共享对象文件与python链接,这就是我遇到一些错误的原因。请您提供执行此操作的步骤。这将非常有用。谢谢。包含所有文件与这个项目相关的。我认为你正确地链接到OpenCvsCub,但是它可能不包含符号。你必须链接它以使它作为C++程序构建?在Linux上(并且可能是OSX)。您可以使用
ldd ela_c.so
查看模块链接到的库,并使用
objdump-T/path/to/libopencv.so
获取库中的符号列表。如果符号不在库中,则需要在其他地方找到它。