如何绘制每个分割对象的轮廓

2024-06-18

我应用分水岭分割来检测触摸对象,这样做效果很好。现在,我想绘制每个对象的轮廓,这样我就可以获得它们的长度、面积、矩等。但是分割结果中的对象仍然是触摸的。所以,我没能画出每一个的轮廓。如何绘制每个对象的轮廓?

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

using namespace std;
using namespace cv;

int main()
{
    Mat src = imread("source.png");

    // Create binary image from source image
    Mat srcGray;
    cvtColor(src, srcGray, CV_BGR2GRAY);

    Mat srcThresh;
    threshold(srcGray, srcThresh, 0, 255, CV_THRESH_BINARY | CV_THRESH_OTSU);

    // Perform the distance transform algorithm
    Mat dist;
    distanceTransform(srcThresh, dist, CV_DIST_L2, 3);

    // Normalize the distance image for range = {0.0, 1.0}
    normalize(dist, dist, 0, 1., NORM_MINMAX);

    // Threshold to obtain the peaks 
    threshold(dist, dist, 0.1, 3.5, CV_THRESH_BINARY);

    // Create the CV_8U version of the distance image
    Mat dist_8u;
    dist.convertTo(dist_8u, CV_8U);

    // Find total markers
    std::vector<std::vector<Point> > contours;
    findContours(dist_8u, contours, CV_RETR_EXTERNAL, CV_CHAIN_APPROX_SIMPLE);
    int ncomp = contours.size();

    // Create the marker image for the watershed algorithm
    Mat markers = Mat::zeros(dist.size(), CV_32SC1);

    // Draw the foreground markers
    for (int i = 0; i < ncomp; i++)
        drawContours(markers, contours, i, Scalar::all(i + 1), -1);

    // Draw the background marker
    circle(markers, Point(5, 5), 3, CV_RGB(255, 255, 255), -1);

    // Perform the watershed algorithm
    watershed(src, markers);

    Mat wgResult = (markers.clone()) * 10000;

    imshow("Watershed", wgResult);

    waitKey(0);
    return 0;
}

Source image: enter image description here

Watershed Result: enter image description here


The markers返回的矩阵watershed根据种子,包含分段区域的索引。所以每个成分将具有相同的种子值。然后,您可以为每个种子创建一个二进制矩阵,例如:

Mat1b mask = (markers == seed);

一旦你有了每个组件的二进制掩码,你就可以轻松计算它的面积、力矩等......

Code:

#include <opencv2/opencv.hpp>
#include <iostream>
using namespace std;
using namespace cv;

int main()
{
    Mat src = imread("D:\\SO\\img\\postit.png");

    // Create binary image from source image
    Mat srcGray;
    cvtColor(src, srcGray, CV_BGR2GRAY);

    Mat srcThresh;
    threshold(srcGray, srcThresh, 0, 255, CV_THRESH_BINARY | CV_THRESH_OTSU);

    // Perform the distance transform algorithm
    Mat dist;
    distanceTransform(srcThresh, dist, CV_DIST_L2, 3);

    // Normalize the distance image for range = {0.0, 1.0}
    normalize(dist, dist, 0, 1., NORM_MINMAX);

    // Threshold to obtain the peaks 
    threshold(dist, dist, 0.1, 3.5, CV_THRESH_BINARY);

    // Create the CV_8U version of the distance image
    Mat dist_8u;
    dist.convertTo(dist_8u, CV_8U);

    // Find total markers
    std::vector<std::vector<Point> > contours;
    findContours(dist_8u, contours, CV_RETR_EXTERNAL, CV_CHAIN_APPROX_SIMPLE);
    int ncomp = contours.size();

    // Create the marker image for the watershed algorithm
    Mat markers = Mat::zeros(dist.size(), CV_32SC1);

    // Draw the foreground markers
    for (int i = 0; i < ncomp; i++)
        drawContours(markers, contours, i, Scalar::all(i + 1), -1);

    // Draw the background marker
    circle(markers, Point(5, 5), 3, CV_RGB(255, 255, 255), -1);

    // Perform the watershed algorithm
    watershed(src, markers);

    for (int seed = 1; seed <= ncomp; ++seed)
    {
        Mat1b mask = (markers == seed);

        // Now you have the mask, you can compute your statistics

        imshow("Mask", mask);
        waitKey();
    }

    return 0;
}
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

如何绘制每个分割对象的轮廓 的相关文章

  • OpenSSL:RSA 加密/解密、密钥生成和密钥持久性

    我正在尝试构建一个需要以下内容的 p2p 应用程序 在 OpenSSL 中使用 RSA Encryption Decryption Generating Keys done Saving and loading keys done Savi
  • 为什么这个 IA32 汇编代码有 3 个 leaal 指令?

    我编译了这个C函数 int calc int x int y int z return x 3 y 19 z 我在 calc s 中得到了这个 我正在注释正在发生的事情 file calc c text globl calc type ca
  • 具有自动返回类型推导的 Friend 函数模板无法访问私有成员

    抱歉这个问题的标题太复杂了 我试图描述我为这个问题构建的最小 SSCCE 我有以下代码 include
  • 嵌套绑定表达式

    这是一个后续问题我之前的问题 https stackoverflow com questions 2735294 templates function pointers and c0x include
  • Linq Any 始终返回 true

    我已经使用 Linq to Entities 多年 但这是我第一次遇到这个问题 我有Tips and Items表 每个提示可以有很多项目 我的数据库中只有 3 个项目 编辑项目时 我想确保GivenId对于具有相同提示的项目 字段是唯一的
  • 如何更改控制台中的光标位置?

    我想用Console ReadLine 在上一行中并使其显示如下 HeresomeText gt input Not like HeresomeText gt input 可以做吗 使用 Write 方法而不是 WriteLine 方法 C
  • 文件已创建但无法写入

    我的计划 检查Settings txt 文件 如果该文件不存在 则创建文本并自动写入其中 如果 Settings txt 文件已存在 请忽略 不要创建或写入现有文件 我的问题 当文件不存在时 Settings txt 文件会创建 但它是空的
  • C++ 访问嵌套类的私有成员

    标题可能有点误导 我有以下问题 我有一棵由叶子和内部节点组成的树 用户应该能够在叶子中存储任何信息and该树有一些方法可以获取一组用户定义的值 并且需要在恒定时间内 未摊销 访问相应的叶子 我提出了以下想法 但它不起作用 因为不幸的是我无法
  • “双免”是什么意思?

    正如标题所暗示的那样 我是 C 语言的新手 并且很快就会有期中考试 我目前正在修改过去的论文 一个反复出现的主题是双重自由问题 我理解就是调用的过程free 在同一个内存位置两次 但我有几个问题我不能 100 确定如何回答 问题1 C中双重
  • 使用 Opencv 屏蔽水平线和垂直线

    我正在尝试删除该图像中的水平线和垂直线 以便拥有更清晰的文本区域 我正在使用下面的代码 它遵循这个guide https docs opencv org 3 2 0 d1 dee tutorial moprh lines detection
  • 从高斯分布中采样随机值的最快方法是什么?

    The Box Muller 变换 http en wikipedia org wiki Box E2 80 93Muller transform 是一种从高斯分布中采样随机值的优雅且性能合理的方法 我正在寻找一种用 C 编写 清晰的更快方
  • 访问控制器类中的 appsettings.json 值

    无法弄清楚如何读取startup cs之外的appsettings json值 例如 我想做的是在 Layout cshtml 中 从配置中添加站点名称 例如 ViewData SiteName Configuration GetValue
  • 是否可以使用 struct stat 描述符获取和设置文件名?

    是否可以在获取或设置 重命名 文件名时给出文件的绝对路径 并将 struct stat 实例作为 lstat 函数的参数 正如我在文档结构中发现的那样 struct stat dev t st dev ID of device contai
  • 如何打开 Outlook 已接收和阅读电子邮件

    我们有 5 个人 使用同一封电子邮件通过 Outlook 回复客户 我想设计一个程序来打开所有已发送的电子邮件 阅读它们 打开它们 找到第一个人的签名 并在他 她的计数器中添加一个数字 以便我可以得出一些统计数据 关于如何打开 Outloo
  • 我如何在 WPF 中模仿这种行为?

    我对 WPF 和 C 开发相当陌生 我正在制作这个应用程序 我不知道是否有人熟悉 VOIP App Discord 但他们有一个我非常喜欢的特定行为 并且想尝试使用 WPF 创建类似的风格 当您在 Discord 上添加服务器时 单击一个按
  • 如何在迭代时从地图中删除?

    迭代时如何从地图中删除 喜欢 std map
  • 对数据绑定组合框进行排序的最佳方法是什么?

    我对此做了一些研究 似乎对数据绑定组合框进行排序的唯一方法是对数据源本身进行排序 在本例中为数据集中的数据表 如果是这种情况 那么问题就变成对数据表进行排序的最佳方法是什么 组合框绑定在设计器中设置初始化使用 myCombo DataSou
  • 类型与创建 CLR 存储过程不匹配

    我在程序集中有一个如下所示的方法 namespace MyNameSpace public class MyClass Microsoft SqlServer Server SqlProcedure public static void M
  • 找出用户属于哪些组

    我有一个刚刚创建的 Windows 用户帐户 以 XYZ 为例 此 XYZ 属于我在计算机管理 gt 本地用户和组中创建的用户组和自定义组 因此 在属性中我看到该用户属于 2 个组 现在我想获取这些组并显示它们 有什么建议么 我已经这样做了
  • 从 C# 调用 C++ DLL

    我想使用 C 中的 C DLL C DLL 是win32 控制台应用程序 我已成功调用它 并希望在 C 中处理来自 C 的数据 然而 C 应用程序在执行 DLL 后退出 即这一行 GetArrayFromDLL 我是 C 和 Visual

随机推荐

  • 加载 DLL 及其依赖项

    如何加载 dll 及其依赖项 我不想将每个依赖的 dll 都放在 Assembly Load 中 我宁愿只加载一个 dll 然后加载依赖项 当我的应用程序启动时 上面的 dll 不会被加载 它们仅在用户执行特定操作时加载 然后冻结 gui
  • Delphi 6 命令行编译:无 DCU

    当对 dpr 文件使用 dcc32 时 它会生成一个 dll 但不会生成 dcu 项目级别 cfg 使用 N 开关设置路径 但指定的目录中没有任何内容 当 E 开关正在工作时 它必须看到 cfg 我尝试在调用 dcc32 之前对 dpr 文
  • 如何知道我的页面是否在 Facebook iframe 中运行

    我目前正在开发一个独立运行的网站 并作为 iframe 上的 Facebook 应用程序运行 我想知道在页面加载之前检查我的页面是否在 facebook iframe 中运行的 最佳实践 是什么 以便我可以预设相关的 CSS 和其他变量 T
  • 如何循环遍历 JSON 数组?

    我有一些 JSON 代码 其中包含多个对象 MNGR NAME Mark MGR ID M44 EMP ID 1849 MNGR NAME Steve PROJ ID 88421 PROJ NAME ABC PROJ ALLOC NO 49
  • 将字符串限制为逗号后 2 个数字且仅限 1 个逗号

    我有下面的脚本 只允许输入文本上的数字和逗号 function validate evt var theEvent evt window event var key theEvent keyCode theEvent which key S
  • UdpClient 在多个侦听器上接收数据

    我有一个实现自动发现机制的应用程序 但我遇到了 UdpClient 问题 只要应用程序的单个实例打开 它就可以正常工作 然而 当第二个实例打开时 只有第一个实例接收单播数据包 有趣的是 实现相同机制的类似应用程序似乎没有这个问题 有什么建议
  • 如何从react-native webview获取选择对象

    我有一个应用程序 我使用反应本机 webview 来显示文档 用户可以选择一些文本并执行我提供的一些自定义操作 如何从 webview 获取选择对象into my app 从 0 37 0 开始 RN 中的一个新功能可能会对您有所帮助 里面
  • Android REST API 连接

    我有点傻 对此感到抱歉 我编写了一个 API 它返回一些 JSON 我的目标是从 Android 应用程序使用此 API 我已经尝试过使用 AsyncTask 但失败了 我想像这样使用它 调用该类 告知 URL 和结果的类型 哪个json
  • 为什么三元运算符在自动拆箱时会抛出 NPE? [复制]

    这个问题在这里已经有答案了 在下面的测试中 getDummyAge 不应评估方法 因为testage变量总是null public class IntegerTest Test public void intergerTestFailure
  • Raphaël.js 中的剪辑路径

    我怎样才能像这样将 Clip path 与 Rapha l js 一起使用example http www simplesystems org RMagick doc ex clip path gif 看来 Raphael js 中只有 C
  • Swift:本地化字符串数组

    我有一个包含 100 多个字符串的数组 其设置如下所示 有什么方法可以本地化数组中的所有字符串 或者这是设置它的更好方法吗 var listOfThings Cars Mopeds 我建议将字符串放入 plist 文件中 然后可以根据需要本
  • 如何动态创建 Dapper 查询的参数

    我有一个值字典 例如 Name Alex 有没有办法将其作为查询参数传递给 Dapper 这是一个显示我想要做什么的示例 IDictionary
  • POINT 列上的 MySQL INSERT/UPDATE

    我正在尝试用我国家的地理位置填充我的数据库 我的一张表有 4 个字段 ID PK 纬度 经度和地理点 EDIT SCDBs Punto Geografico SET lat 18 469692 SET lon 63 93212 SET g
  • 使用 Google 脚本移动 Google Drive 中的文件

    我正在尝试使用通过 Google 表单发布的信息创建文档 然后在创建文档后 我想将该文档移至共享文件夹中以供人们查看 目前 我的脚本从 Google Forms 链接的电子表格中获取所有信息 使用该信息 我使用以下代码来创建文档 var t
  • sscanf("123456789123456789123456789", "%d", &n) 是否有定义的行为?

    When sscanf 或来自的另一个函数scanffamily 被赋予一个数字序列 其转换后的值超过目标整数类型的最大值 是否应该认为转换失败 行为是否已被定义 根据标准 7 21 6 2p10 f scanf 适用于整个家庭 如果这个对
  • ExecutorService 应该是静态的和全局的

    我想在我的应用程序中使用相同的线程池 为此 我可以使ExecutorService静态和全局 以便我可以调用ThreadUtil executorService to get ExecutorService当我需要它的时候 public c
  • 在 docker 构建期间设置 DNS 选项

    由于本地网络配置 我必须将 dns 和 dns search 选项添加到我的 docker run 命令中 如下所示 docker run dns XX XX 1 1 dns search companydomain t mycontain
  • 需要野科切吗?没有要加载的文件

    我正在尝试开始使用 Nokogiri 我运行了命令 gem install nokogiri 作为 Windows 7 64 位 中的管理员 控制台显示 已成功安装 和 已安装 1 个 gem 当我输入时 gem list local OR
  • Plesk 11 强制重定向到非 www

    我已经订购了装有 Plesk 11 的新专用服务器 将我的网站从旧服务器移至新服务器 但在打开网站时遇到一些问题 使用 htaccess 我强制客户端使用带有 www 的网站 Plesk 默认情况下执行相反的操作 www 到非 www 结果
  • 如何绘制每个分割对象的轮廓

    我应用分水岭分割来检测触摸对象 这样做效果很好 现在 我想绘制每个对象的轮廓 这样我就可以获得它们的长度 面积 矩等 但是分割结果中的对象仍然是触摸的 所以 我没能画出每一个的轮廓 如何绘制每个对象的轮廓 include