OpenCV计算形状之间的相似度ShapeContextDistanceExtractor类的使用

  • 操作系统:ubuntu22.04
  • OpenCV版本:OpenCV4.9
  • IDE:Visual Studio Code
  • 编程语言:C++11

1.功能描述

ShapeContextDistanceExtractor是OpenCV库中的一个类,主要用于计算形状之间的相似度或距离。它是基于形状上下文(Shape Context)特征描述符的,这是一种在计算机视觉和图像处理领域广泛使用的形状匹配技术。该方法由Belongie等人在2000年代初提出,通过分析形状边界点的邻域分布来描述形状特征,进而计算形状间的相似度。

2.使用场景

形状匹配 :在图像数据库中查找相似的形状或对象。
物体识别 :作为特征提取的一部分,辅助分类或识别任务。
内容基于的图像检索:根据形状内容搜索图像。

3.函数computeDistance

计算由其轮廓定义的两个形状之间的形状距离,首先提取每个轮廓的关键点及其邻域信息,然后通过比较不同轮廓间对应关键点的邻域分布差异来量化形状间的距离。

3.1函数原型

cpp 复制代码
virtual float cv::ShapeDistanceExtractor::computeDistance	(
InputArray 	contour1,
InputArray 	contour2 
)		

3.2 参数

  • 参数contour1 定义第一个形状的轮廓.
  • 参数contour2 定义第二个形状的轮廓...

4 示例代码

cpp 复制代码
#include "opencv2/highgui.hpp"
#include "opencv2/imgcodecs.hpp"
#include "opencv2/imgproc.hpp"
#include "opencv2/shape.hpp"

#include <iostream>
#include <opencv2/core/utility.hpp>
#include <string>
using namespace std;
using namespace cv;

static vector< Point > simpleContour( const Mat& currentQuery, int n = 300 )
{
    vector< vector< Point > > _contoursQuery;
    vector< Point > contoursQuery;
    findContours( currentQuery, _contoursQuery, RETR_LIST, CHAIN_APPROX_NONE );
    for ( size_t border = 0; border < _contoursQuery.size(); border++ )
    {
        for ( size_t p = 0; p < _contoursQuery[ border ].size(); p++ )
        {
            contoursQuery.push_back( _contoursQuery[ border ][ p ] );
        }
    }
    // In case actual number of points is less than n
    int dummy = 0;
    for ( int add = ( int )contoursQuery.size() - 1; add < n; add++ )
    {
        contoursQuery.push_back( contoursQuery[ dummy++ ] );  // adding dummy values
    }
    // 均匀采样
    cv::randShuffle( contoursQuery );
    vector< Point > cont;
    for ( int i = 0; i < n; i++ )
    {
        cont.push_back( contoursQuery[ i ] );
    }
    return cont;
}
int main( int argc, char** argv )
{
    string path = "/media/dingxin/data/study/OpenCV/sources/images/shape/";
  
    cv::Ptr< cv::ShapeContextDistanceExtractor > mysc = cv::createShapeContextDistanceExtractor();
    Size sz2Sh( 300, 300 );
    stringstream queryName;
    int indexQuery = 1;
    queryName << path << indexQuery << ".jpg";
    Mat query = imread( queryName.str(), IMREAD_GRAYSCALE );
    Mat queryToShow;
    resize( query, queryToShow, sz2Sh, 0, 0, INTER_LINEAR_EXACT );
    imshow( "QUERY", queryToShow );
    moveWindow( "TEST", 0, 0 );
    vector< Point > contQuery = simpleContour( query );
    int bestMatch             = 0;
    float bestDis             = FLT_MAX;
    for ( int ii = 1; ii <= 4; ii++ )
    {
        if ( ii == indexQuery )
            continue;
        waitKey( 30 );
        stringstream iiname;
        iiname << path << ii << ".jpg";
        cout << "name: " << iiname.str() << endl;
        Mat iiIm = imread( iiname.str(), 0 );
        Mat iiToShow;
        resize( iiIm, iiToShow, sz2Sh, 0, 0, INTER_LINEAR_EXACT );
        imshow( "TEST", iiToShow );
        moveWindow( "TEST", sz2Sh.width + 50, 0 );
        vector< Point > contii = simpleContour( iiIm );
        float dis              = mysc->computeDistance( contQuery, contii );
        //获取匹配度最佳的id和匹配距离值
        if ( dis < bestDis )
        {
            bestMatch = ii;
            bestDis   = dis;
        }
        std::cout << " distance between " << queryName.str() << " and " << iiname.str() << " is: " << dis << std::endl;
    }
    destroyWindow( "TEST" );
    stringstream bestname;
    bestname << path << bestMatch << ".jpg";
    Mat iiIm = imread( bestname.str(), 0 );
    Mat bestToShow;
    resize( iiIm, bestToShow, sz2Sh, 0, 0, INTER_LINEAR_EXACT );
    imshow( "BEST MATCH", bestToShow );
    moveWindow( "BEST MATCH", sz2Sh.width + 50, 0 );
    waitKey();
    return 0;
}

运行结果

我一共选了4张图,拿第一张图跟其他三张图比较,看哪个图跟第一张图里的足球形状匹配的最好。四张图如下:

运行结果:

命令行输出结果:

相关推荐
资源大全免费分享12 分钟前
MacOS 的 AI Agent 新星,本地沙盒驱动,解锁 macOS 操作新体验!
人工智能·macos·策略模式
跳跳糖炒酸奶30 分钟前
第四章、Isaacsim在GUI中构建机器人(2):组装一个简单的机器人
人工智能·python·算法·ubuntu·机器人
AI.NET 极客圈34 分钟前
AI与.NET技术实操系列(四):使用 Semantic Kernel 和 DeepSeek 构建AI应用
人工智能·.net
Debroon38 分钟前
应华为 AI 医疗军团之战,各方动态和反应
人工智能·华为
俊哥V39 分钟前
阿里通义千问发布全模态开源大模型Qwen2.5-Omni-7B
人工智能·ai
果冻人工智能1 小时前
每一条广告都只为你而生: 用 人工智能 颠覆广告行业的下一步
人工智能
掘金安东尼1 小时前
GPT-4.5 被 73% 的人误认为人类,“坏了?!我成替身了!”
人工智能·程序员
掘金一周1 小时前
金石焕新程 >> 瓜分万元现金大奖征文活动即将回归 | 掘金一周 4.3
前端·人工智能·后端
白雪讲堂2 小时前
AI搜索品牌曝光资料包(精准适配文心一言/Kimi/DeepSeek等场景)
大数据·人工智能·搜索引擎·ai·文心一言·deepseek
斯汤雷2 小时前
Matlab绘图案例,设置图片大小,坐标轴比例为黄金比
数据库·人工智能·算法·matlab·信息可视化