Ho due tabelle che desidero unire tramite un timestamp, tuttavia i timestamp non vengono registrati esattamente nello stesso momento. Pertanto, desidero unire tutti i timestamp che si trovano entro 5 minuti l'uno dall'altro. Se il timestamp non ha un timestamp corrispondente nell'altra tabella, desidero comunque mantenere i dati della riga. C'è un modo semplice per farlo in JSL?
Potresti creare una colonna formula in ogni tabella dati che arrotonda la colonna timestamp ai 5 minuti più vicini e quindi utilizzare tali colonne per il join.In JMP 14 se fai clic con il pulsante destro del mouse sull'intestazione della colonna timestamp, quindi selezioni Nuova colonna formula->Trasforma->Arrotonda..., ti verrà presentata una finestra di dialogo che ti offre la possibilità di arrotondare per eccesso, per difetto o all'incremento temporale più vicino desiderato.Se non disponi di JMP 14, la formula per arrotondare all'intervallo di 5 minuti più vicino sarebbe simile a questa:
Rotondo( :Timestamp / 300 ) * 300
(Nota che 300 è il numero di secondi in 5 minuti).
La finestra di dialogo Tabelle->Generatore di query JMP (o Tabelle->Unisci) dispone di opzioni per mantenere le non corrispondenze e creare una colonna Flag di corrispondenza.
Spero che questo ti aiuti.
Non esiste una piattaforma integrata che effettuerà un'unione con corrispondenza fuzzy poiché hai dichiarato ciò di cui hai bisogno.Tuttavia, JSL può essere utilizzato per ottenere ciò di cui hai bisogno.
Ecco un esempio approssimativo di un modo per scrivere la tua richiesta
Names Default To Here( 1 );
// Create sample data tables
dt1 = New Table( "Data Table 1",
Add Rows( 100 ),
New Column( "DateTime",
Numeric,
"Continuous",
Format( "m/d/y h:m", 19 ),
Input Format( "m/d/y h:m" ),
Formula( Today() + Row() * In Minutes( 5 ) ),
Set Selected
)
);
dt1 << run formulas;
dt1:DateTime << delete formula;
dt2 = dt1 << Subset(
Sampling Rate( 0.25 ),
Selected columns only( 0 ),
output table name( "Data Table 2" ),
link to original table( 0 )
);
Current Data Table( dt2 );
For Each Row( :DateTime = :DateTime + In Minutes( Random Uniform( -100, 100 ) ) );
dt2 << sort( by( :DateTime ), order( ascending ), replace table( 1 ) );
// Create a column in data table 1 for reference
dt1 << New Column( "RowNum", formula( Row() ) );
dt1:RowNum << delete formula;
// Create in data table 2 a column that will hold the row to join to
dt2 << New Column( "Match Row" );
// Loop through data table 2 and find the rows in the first table that match
For( i = 1, i <= N Rows( dt2 ), i++,
checkVal = dt2:DateTime[i];
theRows = dt1 << get rows where(
:Datetime > checkVal - In Minutes( 5 ) & :DateTime < checkVal + In Minutes( 5 )
);
If( N Rows( theRows ) > 0,
minList = {};
For( k = 1, k <= N Rows( theRows ), k++,
Insert Into( minList, Abs( dt1:DateTime[theRows[k]] - checkVal ) )
);
dt2:Match Row[i] = theRows[Loc( minList, Min( minList ) )];
,
dt2:Match Row[i] = 0
);
);
// Join the tables
dt3 = dt1 << Join(
With( dt2 ),
Merge Same Name Columns,
By Matching Columns( :RowNum = :Match Row ),
Drop multiples( 0, 0 ),
Include Nonmatches( 1, 1 ),
Preserve main table order( 1 ),
output table name("Final Table")
);