GPS yörüngesindeki aykırı değerlerin algılanması ve sabitlenmesi


9

latitude longitude Sonradan düzeltilebilir (komşularına dayalı trajektör yoluna geri getirilebilir) sonradan işleme sırasında bir yörüngedeki aykırı noktaları tespit edebilen bir algoritma veya yöntem bulmak gerekir .

Tespit etmek ve düzeltmek istediğim aykırı noktalara bir örnek olarak, aşağıdakileri gösteren bir resim ekledim:

Ham veriler mavi.

Verileri olabildiğince en iyi şekilde düzeltmek için kokusuz bir Kalman filtresi kullanmayı denedim, ancak bu daha aşırı aykırı değerler (mavi renkte ham veriler, kırmızı renkte düzgünleştirilmiş veriler) için yeterince etkili görünmüyor:

Ham veriler mavi, UKF verileri kırmızı renkte düzeltti.

UKF'm doğru şekilde kalibre edilmemiş olabilir (ancak bunun olduğundan eminim).

Yörüngeler, yürüteçler, koşucular, bisikletçilerdir - başlayıp durdurulabilen, ancak hızla veya aniden hızla veya pozisyonda büyük ölçüde değişmeyen insan gücüyle hareket eder.

Zamanlama verilerine (ve yalnızca konum verilerine) dayanmayan bir çözüm son derece yararlı olacaktır (işlenmekte olan veriler her zaman zamanlama verileri içermeyebileceğinden). Ancak, bu tür bir çözümün ne kadar olası olduğunun farkındayım, bu yüzden herhangi bir çözüm bulduğum için aynı derecede mutluyum!

İdeal olarak, çözüm, aykırı değeri tespit edebilmek için tespit ederek düzeltilmiş bir yörünge oluşturur:

Ham veriler yeşil olarak düzeltildi.


Ele geçirdiğim kaynaklar:

Yanıtlar:


1

Nehir ağlarını işlemek için bir aracın parçası olarak, ağda "ani yükselişler" aramak için bir kalite kontrol aracı oluşturdum. (Nehir ağlarını işlemek için olduğu gibi) aracımı kullanmanızı önermese de , yaptığım şeyin bir görüntüsünü gösteren Yardım dosyasına işaret ediyorum.

Bir çoklu hattın her çizgi parçası arasındaki ardışık açıları tanımlamak için kosinüs yasasını kullanarak kod geliştirdim . Bir çoklu çizgi boyunca ilerlemek ve aşırı açıları tanımlamak için bu fikir etrafında kendi kodunuzu geliştirebilirsiniz .


Açıkladığınız gibi bir yöntem kullandım (kosinüs yasasını kullanarak) ve aykırı değerleri daha iyi belirlemek için noktalar arasındaki mesafeleri dahil ettim ve çok iyi çalışıyor gibi görünüyor. Teşekkür ederim!
JP

8

Algoritma kullanıyorum.

  1. Öklid minimum yayılan nokta ağacını hesaplayın:

resim açıklamasını buraya girin

  1. Bu ağda birbirinden en uzak 2 noktayı bulun

resim açıklamasını buraya girin

  1. Aralarındaki en kısa rotayı bulun:

resim açıklamasını buraya girin

Görüldüğü gibi keskin bir dönüşle köşeyi kesebilir.

Yukarıdaki algoritmanın ArcGIS python uygulaması var, networkx modülünü kullanıyor. Bu ilginizi çektiğini bana bildirin ve cevabımı senaryo ile güncelleyeceğim

GÜNCELLEME:

# Connects points to make polyline. Makes 1 line at a time
# Tool assumes that 1st layer in Table of Conternt is TARGET polyline feature class,
# second layer in TOC is SOURCE point fc.
# If no selection found in SOURCE layer, works on entire dataset

import arcpy, traceback, os, sys
import itertools as itt
from math import sqrt
sys.path.append(r'C:\Users\felix_pertziger\AppData\Roaming\Python\Python27\site-packages')
import networkx as nx
from networkx import dijkstra_path_length

try:
    def showPyMessage():
        arcpy.AddMessage(str(time.ctime()) + " - " + message)
    def CheckLayerLine(infc):
        d=arcpy.Describe(infc)
        theType=d.shapeType
        if theType!="Polyline":
            arcpy.AddWarning("\nTool designed to work with polylines as TARGET!")
            raise NameError, "Wrong input\n"
        return d
    def CheckLayerPoint(infc):
        d=arcpy.Describe(infc)
        theType=d.shapeType
        if theType!="Point":
            arcpy.AddWarning("\nTool designed to work with points as SOURCE!")
            raise NameError, "Wrong input\n"
        return d
    mxd = arcpy.mapping.MapDocument("CURRENT")
    layers = arcpy.mapping.ListLayers(mxd)
    if len(layers)<=1:
        arcpy.AddWarning("\nNot enough layers in the view!")
        raise NameError, "Wrong input\n"
    destLR, sourceLR=layers[0],layers[1]
    a = CheckLayerPoint(sourceLR);d = CheckLayerLine(destLR)

#  copy all points to manageable list
    g=arcpy.Geometry()
    geometryList=arcpy.CopyFeatures_management(sourceLR,g)
    nPoints=len(geometryList)
    arcpy.AddMessage('Computing minimum spanning tree')
    list2connect=[p.firstPoint for p in geometryList]
#  create network    
    p=list(itt.combinations(range(nPoints), 2))
    arcpy.SetProgressor("step", "", 0, len(p),1)
    G=nx.Graph()
    for f,t in p:
        p1=list2connect[f]
        p2=list2connect[t]
        dX=p2.X-p1.X;dY=p2.Y-p1.Y
        lenV=sqrt(dX*dX+dY*dY)
        G.add_edge(f,t,weight=lenV)
        arcpy.SetProgressorPosition()
    arcpy.AddMessage(len(G.edges()))
    mst=nx.minimum_spanning_tree(G)
    del G

#  find remotest pair
    arcpy.AddMessage(len(mst.edges()))
    length0=nx.all_pairs_dijkstra_path_length(mst)
    lMax=0
    for f,t in p:
        lCur=length0[f][t]
        if lCur>lMax:
            lMax=lCur
            best=(f,t)
    gL=nx.dijkstra_path(mst,best[0],best[1])
    del mst
    nPoints=len(gL)
    ordArray=arcpy.Array()
    for i in gL: ordArray.add(list2connect[i])

#  append line to TARGET
    curT = arcpy.da.InsertCursor(destLR,"SHAPE@")
    curT.insertRow((arcpy.Polyline(ordArray),))
    arcpy.RefreshActiveView()
    del curT

except:
    message = "\n*** PYTHON ERRORS *** "; showPyMessage()
    message = "Python Traceback Info: " + traceback.format_tb(sys.exc_info()[2])[0]; showPyMessage()
    message = "Python Error Info: " +  str(sys.exc_type)+ ": " + str(sys.exc_value) + "\n"; showPyMessage()            

Hmmm ilginç bir yaklaşım .. bunu paylaştığınız için teşekkürler! çalışan bir örnek değerli olacaktır eminim!
nickves

1
Bu yaklaşımın sonucu ile sadece giriş verilerini takip ederek elde edeceğiniz şey arasında bir parça parçalı karşılaştırma, “ani yükselmelerden” kurtulan ancak yine de köşeleri koruyacak bir eşik ayarlamanızı sağlayabilir. Bu özellikle, her bir nokta ile ilişkili, doğal olarak bazı günlüklerden kaynaklanan zaman bilginiz varsa yararlı olabilir.
Doug McClean

1
Yeterince adil. Birbirinden n zaman aralığı uzaklıkta olan düğümler arasında bağlantı oluşturmayarak komut dosyasını değiştirmek kolaydır. Ben GPS yolları için değil, başka şeyler için komut dosyası kullanıyorum. İyileştirmenin başka yolları da var, örneğin, üçgenleme, grafikteki bağlantı sayısını büyük ölçüde azaltacak
FelixIP

2
Bu yöntem bazı durumlarda çalışır, ancak bazı yörüngelerin şekilleri, bu yöntemi kullanmanın benim kullanım durumumda mümkün olmadığı anlamına gelir. (Sorunlar, örneğin, bir yörünge, çok sayıda düğüm yok sayıldığından ve zig-zag'lardan dolayı kendiliğinden ikiye katlandığında ortaya çıkar.
JP

1
@JP geriye doğru giden yollar için ham hat
1'in

4

Bir fikir, yolunuzun her bölümünün açılarını (ve belki de uzunluğunu) listeleyen bir komut dosyası oluşturmaktır. Artık her bir segmentin değerlerini doğrudan komşularıyla (ve muhtemelen ikinci komşuları da doğruluğu artırmak için) karşılaştırabilir ve değerlerin verilen bir hazine değerini aştığı tüm noktaları seçebilirsiniz. Son olarak noktaları yolunuzdan silin.


@Hornbydd tarafından açıklanan, açıları belirlemek için kosinüs yasasını kullanarak bunu gerçekleştiren benzer bir yöntem kullandım, ayrıca noktalar arasındaki mesafeyi de dahil etti. Öneri için teşekkürler.
JP

2

Ayrıca dikkate değer Median-5 yöntemidir.

Her x (veya y) koordinatı, sırayla etrafındaki 5 x (veya y) değerin medyanına ayarlanır (yani kendisi, önceki iki değer ve sonraki iki değer).

örneğin x3 = medyan (x1, x2, x3, x4, x5) y3 = medyan (y1, y2, y3, y4, y5) vb.

Yöntem hızlıdır ve veri akışında da kullanımı kolaydır.



0

Verilerinizi Excel'e alabilir veya pandalar ve bayraklar kullanabilir ve / veya gerçekçi olmayan mesafe eşiğini aşan bir önceki noktadan tüm mesafeleri silebilirsiniz.

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.