跳到主要内容

3.5.1 Opencv RVV使用

opencv在RVV上的使用跟x86的使用没有区别,主要是库的差异。

什么是opencv?

OpenCV(Open Source Computer Vision Library)是一个开源的计算机视觉和机器学习软件库,由英特尔公司发起并得到社区的广泛支持。它提供了一个跨平台的编程框架,用于实时的计算机视觉应用开发。常用于:

  • 图像处理和分析
  • 人脸检测和识别
  • 物体检测和跟踪
  • 机器学习应用
  • 视频分析
  • 相机标定和3D重建

常用API示例

读取和显示图像

#include <opencv2/opencv.hpp>
#include <iostream>

int main() {
// 读取图像
cv::Mat image = cv::imread("input.jpg");

if (image.empty()) {
std::cout << "无法读取图像文件" << std::endl;
return -1;
}

// 显示图像
cv::imshow("原始图像", image);
cv::waitKey(0);

// 保存图像
cv::imwrite("output.jpg", image);

return 0;
}

图像基本操作

#include <opencv2/opencv.hpp>

int main() {
cv::Mat image = cv::imread("input.jpg");

// 获取图像信息
int width = image.cols;
int height = image.rows;
int channels = image.channels();

std::cout << "图像尺寸: " << width << "x" << height << std::endl;
std::cout << "通道数: " << channels << std::endl;

// 调整图像大小
cv::Mat resized;
cv::resize(image, resized, cv::Size(640, 480));

// 图像旋转
cv::Point2f center(image.cols/2.0, image.rows/2.0);
cv::Mat rotationMatrix = cv::getRotationMatrix2D(center, 45, 1.0);
cv::Mat rotated;
cv::warpAffine(image, rotated, rotationMatrix, image.size());

cv::imshow("调整大小", resized);
cv::imshow("旋转", rotated);
cv::waitKey(0);

return 0;
}

颜色空间转换

#include <opencv2/opencv.hpp>

int main() {
cv::Mat image = cv::imread("input.jpg");

// BGR转灰度
cv::Mat gray;
cv::cvtColor(image, gray, cv::COLOR_BGR2GRAY);

// BGR转HSV
cv::Mat hsv;
cv::cvtColor(image, hsv, cv::COLOR_BGR2HSV);

// BGR转LAB
cv::Mat lab;
cv::cvtColor(image, lab, cv::COLOR_BGR2LAB);

cv::imshow("原始", image);
cv::imshow("灰度", gray);
cv::imshow("HSV", hsv);
cv::imshow("LAB", lab);
cv::waitKey(0);

return 0;
}

边缘检测

#include <opencv2/opencv.hpp>

int main() {
cv::Mat image = cv::imread("input.jpg", cv::IMREAD_GRAYSCALE);

// Canny边缘检测
cv::Mat edges;
cv::Canny(image, edges, 50, 150);

// Sobel边缘检测
cv::Mat sobelX, sobelY, sobel;
cv::Sobel(image, sobelX, CV_64F, 1, 0, 3);
cv::Sobel(image, sobelY, CV_64F, 0, 1, 3);
cv::magnitude(sobelX, sobelY, sobel);
sobel.convertTo(sobel, CV_8U);

cv::imshow("原始", image);
cv::imshow("Canny边缘", edges);
cv::imshow("Sobel边缘", sobel);
cv::waitKey(0);

return 0;
}

性能对比

对比rvv加速的opencv与没有rvv加速的opencv的性能。

性能测试代码:

#include <opencv2/opencv.hpp>
#include <iostream>
#include <chrono>

int main() {
cv::Mat image = cv::imread("../data/test.jpg");

auto start_time = std::chrono::steady_clock::now();
cv::Mat blob;
cv::resize(image, blob, cv::Size(640, 640));

auto end_time = std::chrono::steady_clock::now();
auto duration = std::chrono::duration_cast<std::chrono::milliseconds>(end_time - start_time);
std::cout << "resize time: " << duration.count() << " ms" << std::endl;

start_time = std::chrono::steady_clock::now();
cv::Mat blob_float;
blob_float = cv::dnn::blobFromImage(image,1.0 / 255.0, cv::Size(640, 640), cv::Scalar(0, 0, 0), false, false,CV_32F);
end_time = std::chrono::steady_clock::now();
duration = std::chrono::duration_cast<std::chrono::milliseconds>(end_time - start_time);
std::cout << "blobFromImage time: " << duration.count() << " ms" << std::endl;

return 0;
}

没有rvv优化的opencv性能:

resize time: 10 ms
blobFromImage time: 51 ms

rvv优化的opencv性能:

resize time: 6 ms
blobFromImage time: 35 ms