Boost几何相交无法正确输出 [英] Boost geometry intersection does not output correctly

查看:76
本文介绍了Boost几何相交无法正确输出的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

从以下代码中,我计算出两个多边形的交点.我希望如果不是多边形,则输出可以为NULL.但是输出为((((240,52.9999),(240,53),(240,53),(240,52.9999)))).这不是多边形.有什么方法可以检查输出是否真的是多边形?

  #include< iostream>#include< deque>#include< vector>#include< boost/geometry.hpp>#include< boost/geometry/geometries/point_xy.hpp>#include< boost/geometry/geometries/polygon.hpp>#include< boost/geometry/io/wkt/wkt.hpp>#include< boost/geometry/algorithms/append.hpp>#include< algorithm>//反向,唯一#include< iostream>#include< string>int main(){typedef boost :: geometry :: model :: d2 :: point_xy< double,boost :: geometry :: cs :: cartesian>point_2d;typedef boost :: geometry :: model :: polygon< point_2d>多边形_2d;多边形_2d绿色;boost :: geometry :: append(green,point_2d(286.188,90.9575));boost :: geometry :: append(green,point_2d(274.902,56.2215));boost :: geometry :: append(green,point_2d(274.238,55.7393));boost :: geometry :: append(green,point_2d(246.908,51.9765));boost :: geometry :: append(green,point_2d(194.477,59.7441));boost :: geometry :: append(green,point_2d(159.213,101.141));boost :: geometry :: append(green,point_2d(203.576,149.537));boost :: geometry :: append(green,point_2d(286.188,90.9575));多边形_2d蓝色;boost :: geometry :: append(blue,point_2d(240,53));boost :: geometry :: append(blue,point_2d(240,-53));boost :: geometry :: append(blue,point_2d(-60,-53));boost :: geometry :: append(blue,point_2d(-60,53));boost :: geometry :: append(blue,point_2d(240,53));boost :: geometry :: correct(绿色);boost :: geometry :: correct(blue);std :: vector< polygon_2d>输出;boost :: geometry :: intersection(绿色,蓝色,输出);std :: cout<<绿色&&蓝色:"<<std :: endl;如果(output.size()){std :: cout<< boost :: geometry :: dsv(output [0])<< std :: endl;std :: cout<< boost :: geometry :: area(output [0])<< std :: endl;}返回0;} 

解决方案

您可以清除无效的几何图形:

  output.erase(std :: remove_copy_if(output.begin(),output.end(),output.begin(),[](polygon_2d const& g){return boost :: geometry :: is_valid(g);}),output.end()); 

现在,结果将为空.

查看 或增强多精度,例如:

  typedef boost :: multiprecision :: number< boost :: multiprecision :: cpp_bin_float< 1024 * 128>oopmh;//这是一个很大的魅力typedef boost :: geometry :: model :: d2 :: point_xy< oopmh,boost :: geometry :: cs :: cartesian>point_2d; 

您会看到我们得到了

 绿色&&蓝色的:((((2.4e + 06,530000),(-600000,530000),(-600000,-530000),(2.4e + 06,-530000),(2.4e + 06,530000)))nan 

因此,看起来非常像我们只是获得了一个奇异点.如果您不希望这样做,那么也许您应该只定义sorts的"epsilon"值,即停止考虑重叠和重叠的阈值.

From the following code I calculate the intersection of two polygons. I hope the output can be NULL if it is not polygon. However the output is (((240, 52.9999), (240, 53), (240, 53), (240, 52.9999))). This is not a polygon. Is there any way to check whether the output is really a polygon??

#include <iostream>
#include <deque>
#include <vector>
#include <boost/geometry.hpp>
#include <boost/geometry/geometries/point_xy.hpp>
#include <boost/geometry/geometries/polygon.hpp>
#include <boost/geometry/io/wkt/wkt.hpp>
#include <boost/geometry/algorithms/append.hpp>

#include <algorithm> // for reverse, unique
#include <iostream>
#include <string>


int main()
{
   typedef boost::geometry::model::d2::point_xy<double,    boost::geometry::cs::cartesian> point_2d;
   typedef boost::geometry::model::polygon<point_2d> polygon_2d;

    polygon_2d green;
    boost::geometry::append(green, point_2d(286.188, 90.9575));
    boost::geometry::append(green, point_2d(274.902, 56.2215));
    boost::geometry::append(green, point_2d(274.238, 55.7393));
    boost::geometry::append(green, point_2d(246.908, 51.9765));
    boost::geometry::append(green, point_2d(194.477, 59.7441));
    boost::geometry::append(green, point_2d(159.213, 101.141));
    boost::geometry::append(green, point_2d(203.576, 149.537));
    boost::geometry::append(green, point_2d(286.188, 90.9575));

    polygon_2d blue;
    boost::geometry::append(blue, point_2d(240, 53));
    boost::geometry::append(blue, point_2d(240, -53));
    boost::geometry::append(blue, point_2d(-60, -53));
    boost::geometry::append(blue, point_2d(-60, 53));
    boost::geometry::append(blue, point_2d(240, 53));

    boost::geometry::correct(green);
    boost::geometry::correct(blue);

    std::vector<polygon_2d> output;
    boost::geometry::intersection(green, blue, output);

    std::cout << "green && blue:" << std::endl;
    if(output.size())
    {
       std::cout<<boost::geometry::dsv(output[0])<<std::endl;
       std::cout<<boost::geometry::area(output[0])<<std::endl;
    }

    return 0;
}

解决方案

You can weed out the invalid geometries:

output.erase(
        std::remove_copy_if(output.begin(), output.end(), output.begin(), [](polygon_2d const&g) { return boost::geometry::is_valid(g); }),
        output.end());

Now, the result will be empty as expected.

See it Live On Coliru


It's interesting to me how "invalid" geometries would result in the first place. As you were probably aware that your polygons are very well chosen:

Let's zoom in a little:

Now, you're likely looking at some floating point accuracy issues, as the same experiment with long long points or boost multiprecision, e.g.:

typedef boost::multiprecision::number<boost::multiprecision::cpp_bin_float<1024*128>> oopmh; // that's a lotta oomph
typedef boost::geometry::model::d2::point_xy<oopmh, boost::geometry::cs::cartesian> point_2d;

You will see that we get

green && blue:
(((2.4e+06, 530000), (-600000, 530000), (-600000, -530000), (2.4e+06, -530000), (2.4e+06, 530000)))
nan

So it looks very much like we just get a singular point of area. If you don't want this, then maybe you should just define an "epsilon" value of sorts, a threshold at which you stop considering an overlap an overlap.

这篇关于Boost几何相交无法正确输出的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆