2 votos

¿Cómo calcular la longitud de la polilínea en kilómetros sin cambiar la proyección de WGS84 (utilizando ArcObjects)?

Tengo la clase de característica Carretera (polilínea) y deseo encontrar aquellas carreteras cuya longitud sea superior a 500 kilómetros.

La proyección de la clase de características está en GCS_WGS_1984 y no quiero cambiar la proyección.

¿Hay alguna forma de calcular la longitud en kilómetros mediante programación sin cambiar la proyección?

1voto

Anthony Cramp Puntos 126

Esto es, en muchos sentidos, un problema sencillo si se conocen los detalles. Si se conoce el área en la que caerá una polilínea, se puede proyectar la polilínea a una Proyección apropiada, y luego encontrar la longitud.

Hace unos años, tuve un problema en el que la línea podía estar en cualquier parte. Esto requería una solución general. Para ello, hice las siguientes funciones. La función GetLength iterará sobre cada segmento de la línea, y calculará la longitud de cada segmento usando la fórmula de Haversine. Esta función funciona para líneas de varias partes sin ningún problema.

/// <summary>
/// Gets the length of a given Polyline. This function assumes that the Line is WGS84 Lat-Long
/// </summary>
/// <param name="polyLine">Input Polyline</param>
/// <returns>Length in KM</returns>
internal static double GetLength(IPolyline polyLine)
{
    Double Distance = 0;
    //first check the Geometry's SR
    ISpatialReference SR = polyLine.SpatialReference;
    int FactoryCode = SR.FactoryCode;
    if (FactoryCode == 4326)//this is in WGS 84 Lat long
    {
        //iterate over the parts of the PolyLine
        IGeometryCollection GeomColl = (IGeometryCollection)polyLine;
        for (int i = 0; i < GeomColl.GeometryCount; i++)
        {
            IGeometry Geom = GeomColl.get_Geometry(i);
            if (Geom.GeometryType == esriGeometryType.esriGeometryPath)
            {
                //Now that we have a Path, we need to find the individual Segments
                ISegmentCollection SegColl = (ISegmentCollection)Geom;
                for (int j = 0; j < SegColl.SegmentCount; j++)
                {
                    ISegment Segment = SegColl.get_Segment(j);
                    if (Segment.GeometryType == esriGeometryType.esriGeometryLine)
                    {
                        //Calculate the length of the segment and add it to running total
                        Distance += GetHaverSineDistance(Segment);
                    }
                }
            }
        }

    }
    else
    {
        throw new Exception("Polyline is not in EPSG:4326");
    }

    return Distance;
}

/// <summary>
/// Returns the distance in kilometers of a segment
/// It's based on the code present at: http://megocode3.wordpress.com/2008/02/05/haversine-formula-in-c/
/// </summary>
/// <param name="seg"> The ISegment whose Length is to be calculated</param>
/// <returns>The length in KM</returns>
private static double GetHaverSineDistance(ISegment seg)
{
    Double R = 6371;
    Double dLat = toRadian(seg.ToPoint.Y - seg.FromPoint.Y);
    Double dLong = toRadian(seg.ToPoint.X - seg.FromPoint.X);

    double a = Math.Sin(dLat / 2) * Math.Sin(dLat / 2) +
        Math.Cos(toRadian(seg.FromPoint.Y)) * Math.Cos(toRadian(seg.ToPoint.Y)) *
        Math.Sin(dLong / 2) * Math.Sin(dLong / 2);
    double c = 2 * Math.Asin(Math.Min(1, Math.Sqrt(a)));
    double d = R * c;

    return d;
}

/// <summary>
/// Convert to Radians.
/// </summary>
/// <param name="val">The angle is degrees</param>
/// <returns>Angle in Radians</returns>
private static double toRadian(double val)
{
    return (Math.PI / 180) * val;
}

1voto

user22814 Puntos 196

Puede utilizar la coclase GeometryServer con la interfaz IGeometryServer3 (en 10.1). Véase GetLengthsPreserveShape y GetLengthsGeodesic . Ambos métodos permiten especificar unidades de longitud y hacer el cálculo sobre el esferoide. El método geodésico sustituirá todos los segmentos de la polilínea por geodésicos. Mientras que el de "preservar la forma" calculará la verdadera longitud geográfica de la polilínea tal y como se ve en la pantalla (como si primero se densificara la polilínea y luego se calculara la longitud geodésica de la misma).

0voto

SCdF Puntos 123

Si no está dispuesto a cambiar la proyección para el cálculo (sin guardar) - que es lo que hago. Pruebe esto: Fórmula Haversine .

i-Ciencias.com

I-Ciencias es una comunidad de estudiantes y amantes de la ciencia en la que puedes resolver tus problemas y dudas.
Puedes consultar las preguntas de otros usuarios, hacer tus propias preguntas o resolver las de los demás.

Powered by:

X