上位机图像处理和嵌入式模块部署(自定义算法)

news/2024/7/21 7:40:36 标签: 图像处理, 人工智能

【 声明:版权所有,欢迎转载,请勿用于商业用途。 联系信箱:feixiaoxing @163.com】

        我们在使用opencv的时候,虽然大部分算法都不需要我们自己重头开始编写,但是总有一些关于我们自己产品的know-how,是之前库里本来就不存在的。所以,这个时候,我们还是希望能够借助于opencv实现一些自定义的算法,这样可以满足客户个性化的需求,也可以提高自己的竞争力。另外,即使是opencv库里面已经有的算法,由于它本身面对的是通用平台,因此很难对相关代码进行专门的硬件优化,所以即使是已经存在的算法,有的时候还是需要重新写一遍,出一个针对专门硬件的加速版本,这都是常有的事情。

1、复用之前的opencv部署步骤

        一开始,我们还是需要创建一个console工程、配置好include目录、配置好lib目录、拷贝好必要的dll文件、准备好测试图片,这些都是少不了的。由于这些内容之前都已经谈到过,所以,这里不再赘述。

2、编写自定义函数

        编写自定义函数的核心主要有三个,第一,相关的数据结构是什么?很明显,在opencv下面,数据的保存方式就是cv::Mat。第二,怎么获取像素值?一般来说,直接使用image.at<uchar>(i,j)的方式,就可以获得像素值。第三,怎么设置像素值,做法和第二点一样,不同的是前面是读取,这个直接赋值给它即可。所以,如果我们需要用它来写一个简单的二值化函数,一般可以这么来做,

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

// self defined image processing function
void customThreshold(const cv::Mat& inputImage, cv::Mat& outputImage, int thresholdValue) 
{
	// make sure this is single channel 
	CV_Assert(inputImage.channels() == 1);

	// copy image
	outputImage = inputImage.clone();

	// loop to check each pixel
	for (int i = 0; i < outputImage.rows; ++i) 
	{
		for (int j = 0; j < outputImage.cols; ++j) 
		{
			// get value
			uchar pixelValue = outputImage.at<uchar>(i, j);

			// set value
			outputImage.at<uchar>(i, j) = (pixelValue > thresholdValue) ? 255 : 0;
		}
	}
}

3、补充完剩余的图像处理代码

        仅仅有customThreshold函数还是不够的,整个项目要想运行起来,还需要读取图片文件、保存图片文件、显示图片文件等内容。所以,我们继续把相关的代码补上即可,

// file starts here
int main() 
{
	// read image
	cv::Mat image = cv::imread("D:/lena.png");

	// check if image has been loaded successfully
	if (image.empty()) 
	{
		std::cout << "unable to load image here" << std::endl;
		return -1;
	}

	// transfer image to gray type
	cv::Mat grayImage;
	cv::cvtColor(image, grayImage, cv::COLOR_BGR2GRAY);

	// transfer gray image to binary image
	cv::Mat binaryImage;
	customThreshold(grayImage, binaryImage, 110);

	// show binary image
	cv::imshow("Binary Image", binaryImage);

	// wait for input
	cv::waitKey(0);
	return 0;
}

        首先,还是和以前一样,通过cv::imread的方法读取图片。接着判断图片是否为空。判断结束后,先是把image转成grayImage,然后把grayImage继续转成binaryImage,最后显示binaryImage即可。当然,这里会调用一下cv::waitKey,没有按键输入的话,图片窗口会一直处于显示状态。

4、编译和测试

        编译的话,主要看编译有没有出错、链接有没有出错、运行有没有出错,如果这几个部分都没有问题,那说明我们前面设置的环境都是ok的。这样,只需要看显示的图片有没有变成二值化即可。另外,也说明我们在完全没有借助opencv api的情况下,自己实现了一个自定义函数,这在后续的产品开发中是非常有用的。


http://www.niftyadmin.cn/n/5342604.html

相关文章

初识node.js(使用)

文章目录 项目目录介绍和运行流程1.index.html&#x1f447;2.整个项目的核心入口文件其实是main.js3.App.vue 组件化开发 和 根组件普通组件的注册1.局部注册2.全局注册 综合案例 项目目录介绍和运行流程 1.index.html&#x1f447; <!DOCTYPE html> <html lang&quo…

时间序列大模型:TimeGPT

论文&#xff1a;https://arxiv.org/pdf/2310.03589.pdf TimeGPT&#xff0c;这是第一个用于时间序列的基础模型&#xff0c;能够为训练期间未见过的多样化数据集生成准确的预测。 大规模时间序列模型通过利用当代深度学习进步的能力&#xff0c;使精确预测和减少不确定性成为…

Python - argparse模块

python中的argparse模块&#xff0c;用于命令后参数解析&#xff0c;方便测试&#xff0c;是python中自带的模块。 可以自动生成帮助文档&#xff0c;和使用手册。而且当用户在执行程序的时候&#xff0c;输入无效的参数时&#xff0c;会给出对应的错误信息。 使用方法&#…

Flink编程——基础环境搭建

基础环境搭建 文章目录 基础环境搭建准备环境搭建源码环境搭建克隆代码编译导入IDEA 集群环境搭建本地模式安装步骤 1&#xff1a;下载步骤 2&#xff1a;启动集群步骤 3&#xff1a;提交作业&#xff08;Job&#xff09;步骤 4&#xff1a;停止集群 总结 准备环境搭建 我们先…

C# .Net6搭建灵活的RestApi服务器

1、准备 C# .Net6后支持顶级语句&#xff0c;更简单的RestApi服务支持&#xff0c;可以快速搭建一个极为简洁的Web系统。推荐使用Visual Studio 2022&#xff0c;安装"ASP.NET 和Web开发"组件。 2、创建工程 关键步骤如下&#xff1a; 包添加了“Newtonsoft.Json”&…

Matlab 将工作区变量保存到文件中(save)

语法 1、save(filename) 2、save(filename,variables) 3、save(filename,variables,fmt) 4、save(filename,variables,version) 5、save(filename,variables,version,-nocompression) 6、save(filename,variables,-append) 7、save(filename,variables,-append,-nocompression…

《微信小程序开发从入门到实战》学习九十一

7.1 视图容器组件 7.1.2 scroll-view组件 scroll-view组件时是滚动的视图容器&#xff0c;可在竖直方向或水平方向上滚动&#xff0c;展示超出屏幕高度或宽度的内容。 使用竖直方向滚动时&#xff0c;需要通过wxss的height样式给scroll-view设置一个固定高度&#xff0c;超出…

数据采集与预处理02 :网络爬虫实战

数据采集与预处理02 &#xff1a;网络爬虫实战 爬虫基本知识 1 HTTP的理解 URL uniform resource locator. 是统一资源定位符&#xff0c;URI identifier是统一资源标识符。几乎所有的URI都是URL。 URL前部一般可以看到是HTTP还是HTTPS&#xff0c; 这是访问资源需要的协议…