我正在尝试使用Java包装器为OpenCV实现分水岭分割。

这是我在做什么:

public void watershedSegmentation(Mat image)
    {
        Mat target =  new Mat(image.rows(), image.cols(), CvType.CV_8UC3);
        Imgproc.cvtColor(image, target, Imgproc.COLOR_BGRA2RGB);

        //Conversion to 8UC1 grayscale image
        Mat grayScale = new Mat(image.rows(), image.cols(), CvType.CV_64FC1);
        Imgproc.cvtColor(image, grayScale, Imgproc.COLOR_BGR2GRAY);


        //Otsu's Threshold, applied to the grayscale image
        Imgproc.threshold(grayScale, grayScale, 0, 255, Imgproc.THRESH_OTSU);

        //constructing a 3x3 kernel for morphological opening
        Mat openingKernel = Mat.ones(3,3, CvType.CV_8U);
        Imgproc.morphologyEx(grayScale, grayScale, Imgproc.MORPH_OPEN, openingKernel, new Point(-1,-1), 3);

        //dilation operation for extracting the background
        Imgproc.dilate(grayScale, grayScale, openingKernel, new Point(-1,-1), 1);


        Imgproc.watershed(target, grayScale);

    }

就在我调用“分水岭”的那一刻,我看到一条错误消息:
OpenCV Error: Unsupported format or combination of formats (Only 32-bit, 1-channel output images are supported) in cvWatershed, file ..\..\..\..\opencv\modules\imgproc\src\segmentation.cpp, line 151
Exception in thread "main" CvException [org.opencv.core.CvException: cv::Exception: ..\..\..\..\opencv\modules\imgproc\src\segmentation.cpp:151: error: (-210) Only 32-bit, 1-channel output images are supported in function cvWatershed
]
    at org.opencv.imgproc.Imgproc.watershed_0(Native Method)
    at org.opencv.imgproc.Imgproc.watershed(Imgproc.java:9732)
    at segmentation.Segmentation.watershedSegmentation(Segmentation.java:60)
    at segmentation.Segmentation.main(Segmentation.java:29)

我明白了,OpenCV正在寻找一个32位1通道文件作为输出。

我尝试了所有可能的组合:
  • CvType.CV_32FC1,
  • CvType.CV_32F,
  • CvType.CV_32S,
  • CvType.CV_32SC1,
  • CvType.CV_8UC1,
  • CvType.CV_16UC1

  • ... 他们全部。

    该错误是有 flex 的。它拒绝走开。

    请帮忙。

    提前致谢。

    最佳答案

    在经过Imgproc.cvtColor(image, grayScale, Imgproc.COLOR_BGR2GRAY);之后,即使使用CV_64F标志创建了灰度矩阵,您的灰度矩阵也很可能是CV_8UC1类型的
    watershed期望第二个矩阵参数是CV_32F矩阵,其中填充了区域的初始种子,请参阅the doc

    [编辑]
    在注释之后,如果您只想运行分水岭,则可以执行以下操作:

    Mat seeds = new Mat(image.rows(), image.cols(), CvType.CV_32FC1);
    for (int i = 0; i < 10; ++i) {
      // initialize 10 random seeds
      seeds.at<float>(rand()%image.rows, rand()%image.cols) = i; // translate that into the Java interface
    }
    Imgproc.watershed(target, seeds);
    

    关于java - OpenCV中分水岭分割的图像格式不匹配,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/24909852/

    10-10 08:57