J'essaye de générer un pandas.DateTimeIndex avec une fréquence d'échantillonnage de 5120 Hz. Cela donne une période de increment=0.0001953125 secondes.

Si vous essayez d'utiliser pandas.date_range(), vous devez spécifier la fréquence (paramètre freq) comme str ou comme pandas.DateOffset. Le premier ne peut gérer qu'une précision jusqu'à 1 ns, le second a une performance terrible par rapport au str et a une erreur encore pire.

Lors de l'utilisation de la chaîne, je construis comme suit:

freq=str(int(increment*1e9))+'N')

Qui exécute mon fichier de 270 Mo en moins de 2 secondes, mais j'ai une erreur (dans le DateTimeIndex) après 3 millions d'enregistrements d'environ 1500 µs.

Lorsque vous utilisez le pandas.DateOffset, comme ceci

freq=pd.DateOffset(seconds=increment)

Il analyse le fichier en 1 minute et 14 secondes, mais a une erreur d'environ une seconde.

J'ai aussi essayé de construire le DateTimeIndex en utilisant

starttime + pd.to_timedelta(cumulativeTimes, unit='s')

Cette somme prend également des siècles à compléter, mais est la seule à ne pas avoir l'erreur dans le DateTimeIndex résultant.

Comment puis-je obtenir une génération performante du DateTimeIndex tout en conservant ma précision?

1
rubdos 13 juil. 2015 à 13:15

2 réponses

Meilleure réponse

J'ai utilisé une implémentation pure numpy pour résoudre ce problème:

accuracy = 'ns'

relativeTime = np.linspace(
        offset,
        offset + (periods - 1) * increment,
        periods)

def unit_correction(u):
    if u is 's':
        return 1e0
    elif u is 'ms':
        return 1e3
    elif u is 'us':
        return 1e6
    elif u is 'ns':
        return 1e9

# Because numpy only knows ints as its date datatype, 
# convert to accuracy.
return (np.datetime64(starttime) 
        + (relativeTime*unit_correction(accuracy)).astype(
            "timedelta64["+accuracy+"]"
            )
        )

(il s'agit de la demande d'extraction github pour les personnes intéressées: https://github.com/adamreeve/npTDMS/ tirer / 31)

0
rubdos 13 juil. 2015 à 13:02

Je pense que j'arrive à un résultat similaire avec la fonction ci-dessous (bien qu'elle n'utilise que la précision nanoseconde):

def date_range_fs(duration, fs, start=0):
    """ Create a DatetimeIndex based on sampling frequency and duration
    Args:
        duration: number of seconds contained in the DatetimeIndex
        fs: sampling frequency
        start: Timestamp at which de DatetimeIndex starts (defaults to POSIX
               epoch)
    Returns: the corresponding DatetimeIndex
    """
    return pd.to_datetime(
        np.linspace(0, 1e9*duration, num=fs*duration, endpoint=False),
        unit='ns',
        origin=start)
0
Tabs 19 janv. 2018 à 15:06