Adatta dati lineari a tratti


18

Qual è un modo affidabile per adattare dati lineari ma rumorosi?

Sto misurando un segnale, che consiste in diversi segmenti quasi lineari. Vorrei adattare in modo atomatico diverse linee ai dati per rilevare le transizioni.

Il set di dati è composto da poche migliaia di punti, con 1-10 segmenti e conosco il numero di segmenti.

Questo è un esempio di ciò che mi piacerebbe fare automaticamente.

inserisci qui la descrizione dell'immagine


Non credo che si possa rispondere a questa domanda in modo ragionevole, a meno che non ci dica in che modo si desidera conoscere le posizioni dei punti di interruzione, qual è il valore stimato per la lunghezza più breve di un segmento lineare e quanti campioni ci sono in un tipico regione di transizione. Se le etichette degli assi orizzontali nella tua figura sono numeri di esempio, quindi, con due transizioni nell'intervallo da a , l'attività è più difficile che se i segmenti di linea retta avessero una durata maggiore (in campioni). x[5]x[0]
Dilip Sarwate,

@DilipSarwate Ho aggiornato la domanda con i requisiti (tra cui la xaxis è il campo magnetico in tesla)
P3trus

Puoi provare questo toolbox se stai lavorando con il toolbox di adattamento della curva
Rhei

Risposte:


12

Ho provato due approcci, ingenuamente (usando solo 3 segmenti). Sicuramente ci sarebbero metodi più fantasiosi là fuori.

    RANSAC, dovrebbe essere un robusto meccanismo di adattamento. È facile arrestare l'algoritmo dopo un numero di segmenti. Tuttavia, potrebbe essere difficile imporre la continuità tra i segmenti - come sembra necessario nella propria applicazione - almeno con una semplice implementazione. Come prova del concetto, ho creato un'immagine dai punti dati in modo da poter utilizzare il motore RANSAC disponibile in , la funzione di rilevamento della linea di Mathematica.iomun'geLioneS

inserisci qui la descrizione dell'immagine

    Montare un modello lineare a tratti usando un minimizzatore per uso generale. È facile imporre la continuità dei segmenti. È interessante notare che i test per i residui e altre proprietà possono fornire informazioni sufficienti per determinare automaticamente il numero di segmenti, ma non l'ho provato. Ecco come appare in Mathematica:

inserisci qui la descrizione dell'immagine


Sembra un'ottima risposta. Grazie per aver contribuito.
Jason R,

7

Non pretendo che il seguente metodo sia robusto, ma potrebbe funzionare per te. Con migliaia di punti e forse una decina di segmenti di linea retta, procedere come segue.X[n]

  • Elaborare i punti per creare un array di bit y [ n ] come segue. y [ n ] = { 1 , se | ( x [ n + 1 ] - x [ n ] ) - ( x [ n ] - x [ n - 1 ] ) | < ϵ , 0 , altrimenti. QuiX[n]y[n]

    y[n]={1,Se |(X[n+1]-X[n])-(X[n]-X[n-1])|<ε,0,altrimenti.
    è un piccolo numero scelto per adattarsi alla tua nozione di quanto vicino a una linea retta vuoi che punti x [ n - 1 ] , x [ n ] , x [ n + 1 ] . Il criterio sarà riconosciuto dai cognoscenti come esigente che la linea retta attraverso ( n - 1 , x [ n - 1 ] ) e ( n , x [ n ] )εX[n-1],X[n],X[n+1](n-1,X[n-1])(n,X[n])(n,X[n])(n+1,X[n+1])
  • y[n]1011ε

  • y[n]X[3]X[88]X[94]X[120]X[129], e così via. Estendi A verso destra e B verso sinistra per scoprire dove si incrociano; estendi B verso destra e C verso sinistra per scoprire dove si intersecano, ecc. Complimenti, ora hai un modello lineare continuo e a tratti per i tuoi dati.


Totalmente rubato la mia risposta! =)
Phonon,

Idea interessante ma purtroppo a causa del rumore sul segnale non ottengo buoni risultati.
P3trus,

1
Quell'espressione il cui magnitute viene confrontato con epsilon è in realtà un'approssimazione alla seconda derivata dei dati. Esistono altri modi per calcolare questo utilizzando più di tre punti che non rispondono al rumore tanto. Cerca Savitzky-Golay.
DarenW,

4

(Anni dopo) le funzioni lineari a tratti sono spline di grado 1, che può essere detto alla maggior parte degli installatori di spline. scipy.interpolate.UnivariateSpline per esempio può essere eseguito con k=1 un parametro di smoothing s, con il quale dovrai giocare - vedi scipy-interpolazione-con-univariate-splines .
In Matlab, vedi come scegliere i nodi .

Aggiunto: trovare nodi ottimali non è facile, perché possono esserci molti optima locali. Invece, dai a UnivariateSpline un obiettivo s, somma dell'errore ^ 2, e lascia che determini il numero di nodi. Dopo il montaggio, get_residual()otterrà la somma effettiva dell'errore ^ 2 e get_knots()i nodi. Una piccola modifica spuò cambiare molto i nodi, specialmente in caso di rumore elevato - ymmv.
La trama mostra adattamenti a una funzione casuale lineare lineare + rumore per vari s.

Per il montaggio di costanti a tratti, vedere Rilevamento gradino . Può essere usato per pw linear? Non lo so; iniziare differenziando i dati rumorosi aumenterà il rumore, sbagliato.

Altre funzioni di test e / o collegamenti a documenti o codice sarebbero i benvenuti. Un paio di collegamenti:
regressione lineare a tratti con parametri come nodi
Le spline lineari sono molto sensibili a dove vengono posizionati i
nodi selezione-nodo-per-spline-regressione cubica
Questo è un problema difficile e la maggior parte delle persone seleziona i nodi per tentativi ed errori.
Un approccio che sta diventando sempre più popolare è utilizzare invece spline di regressione penalizzate.


Aggiunto marzo 2014: la programmazione dinamica è un metodo generale per problemi con sottoproblemi nidificati come questo:

optimal k lines
    = optimal k - 1 lines up to some x
    + cost of the last line x to the end
over x  (all x in theory, nearby x in practice)

La programmazione dinamica è molto intelligente, ma può battere forza bruta + euristica per questo compito?
Vedi le eccellenti note del corso di Erik Demaine in MIT 6.006 Introduzione agli algoritmi e alla regressione lineare segmentata di
Google anche alla sindrome di John Henry.


inserisci qui la descrizione dell'immagine


Il problema, almeno con Scipy, è il posizionamento dei nodi. scipy usa nodi equidistanti.
P3trus,

@ P3trus, sì per cominciare, ma poi possono spostarsi - vedi la trama. Ad ogni modo mira all'errore totale, non ai nodi.
denis,

@ P3trus Hai provato a utilizzare il metodo spline di regressione multivariata che seleziona automaticamente i punti di interruzione in modo iterativo? cs.rtu.lv/jekabsons/regression.html
Atul Ingle

@Atul Ingle, la scelta del punto di interruzione / nodo afaik è lo stesso problema, indipendentemente dall'installatore di spline. Se sei a conoscenza di algoritmi diversi per questo da parte di persone R / regressione, potresti pubblicare un link per favore?
denis,

Sono alla ricerca di pacchetti in R / Matlab che eseguano spline di regressione adattativa? Qui: cran.r-project.org/web/packages/earth/index.html cran.r-project.org/web/packages/mda/index.html e anche ARESLab in Matlab per cui ho già pubblicato il link.
Atul Ingle,

0

Prendi la derivata e cerca aree di valore quasi costante. Dovresti creare l'algoritmo per cercare quelle aree con idealmente un certo livello di pendenza +/- e che ti darebbe la pendenza della linea per quella sezione. Potresti voler eseguire un livellamento, come un mezzo scorrevole, prima di fare la classificazione in sezione. Il prossimo passo sarebbe quello di ottenere l'intersezione y, che dovrebbe essere banale a quel punto.


il derivato potrebbe essere molto rumoroso. non credo che lo consiglierei.
robert bristow-johnson

0

L'uso di un filtro trend l1 è un'altra idea:

Carta

Esempio online


1
La tua risposta è un po 'troppo breve per essere costruttiva! Ti preghiamo di fare uno sforzo per espanderlo in modo pedagogico.
sansuiso,
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.