寻找与SqlGeometryBuilder相反的东西:我如何分解SqlGeometry?

时间:2016-11-28 21:56:03

标签: c# sql-server spatial visitor-pattern sqlgeometry

我知道如何使用SqlGeometry撰写SqlGeometryBuilder ,例如:

// using Microsoft.SqlServer.Types;
SqlGeometryBuilder geometryBuilder = new SqlGeometryBuilder();
geometryBuilder.SetSrid(…);
geometryBuilder.BeginGeometry(OpenGisGeometryType.Polygon);
geometryBuilder.BeginFigure(0, 0);
geometryBuilder.AddLine(…);
…
geometryBuilder.EndFigure();
geometryBuilder.EndGeometry();

SqlGeometry geometry = geometryBuilder.ConstructedGeometry;

构建SqlGeometry之后,它几乎是一个不透明的对象,并检查其组成部分(例如,线条的边界是由它构成的,以及那些线条的终点)使用ST…方法方法(STNumPointsSTPointNSTNumCurvesSTCurveNSTBoundary等)对我来说感觉有点麻烦。

Microsoft.SqlServer.Types或.NET Framework类库中是否存在与SqlGeometryBuilder逻辑相反的内容,即我可以用来分解SqlGeometry 进入其组成部分?我想我正在寻找的东西可能会使用访客模式。

1 个答案:

答案 0 :(得分:1)

Microsoft.SqlServer.Types API 提供与SqlGeometryBuilder相对的功能,格式为the SqlGeometry.Populate(IGeometrySink110) method

此方法接受实现the IGeometrySink110 interface的对象,其定义与SqlGeometryBuilder的定义非常接近。该方法将重播"方法调用在SqlGeometryBuilder上使用以构造SqlGeometry

例如,鉴于上述问题中显示的SqlGeometry geometry,以及以下IGeometrySink110实施:

class ConsoleGeometrySink : IGeometrySink110
{
    public void SetSrid(int srid)
    {
        Console.WriteLine($"SetSrid(srid: {srid})");
    }
    public void BeginGeometry(OpenGisGeometryType type)
    {
        Console.WriteLine($"BeginGeometry(type: {type})");
    }
    public void BeginFigure(double x, double y, double? z, double? m)
    {
        Console.WriteLine($"BeginFigure(x: {x}, y: {y}, z: {z}, m: {m})");
    }
    public void AddCircularArc(double x1, double y1, double? z1, double? m1,
                               double x2, double y2, double? z2, double? m2)
    {
        Console.WriteLine($"AddCircularArc(x1: {x1}, y1: {y1}, z1: {z1}, m1: {m1}, " + 
                                         $"x2: {x2}, y2: {y2}, z2: {z2}, m2: {m2})");
    }
    public void AddLine(double x, double y, double? z, double? m)
    {
        Console.WriteLine($"AddLine(x: {x}, y: {y}, z: {z}, m: {m})");
    }
    public void EndFigure()
    {
        Console.WriteLine($"EndFigure()");
    }
    public void EndGeometry()
    {
        WriteLine($"EndGeometry()");
    }
}

调用geometry.Populate(new ConsoleGeometrySink())会输出以下内容:

SetSrid(srid: …)
BeginGeometry(type: Polygon)
BeginFigure(x: 0, y: 0, z: , m: )
AddLine(…)
…
EndFigure()
EndGeometry()

完全反映了为构建SqlGeometry而执行的原始步骤。