web-dev-qa-db-fra.com

Conservez uniquement la date lorsque vous utilisez pandas.to_datetime

J'utilise pandas.to_datetime pour analyser les dates dans mes données. Pandas représente par défaut les dates avec datetime64[ns] même si ces dates sont uniquement quotidiennes. Je me demande s’il existe un moyen élégant/intelligent de convertir les dates en datetime.date ou datetime64[D] de sorte que, lorsque j’écris les données au format CSV, les dates ne sont pas ajoutées avec 00:00:00. Je sais que je peux convertir le type manuellement, élément par élément:

[dt.to_datetime().date() for dt in df.dates]

Mais c’est vraiment lent, car j’ai beaucoup de lignes et cela annule en quelque sorte le but d’utiliser pandas.to_datetime. Est-il possible de convertir le dtype de la colonne entière en une fois? Ou bien alternativement, pandas.to_datetime prend-il en charge une spécification de précision afin que je puisse me débarrasser de la partie temps tout en travaillant avec des données quotidiennes?

132
user1642513

Depuis la version 0.15.0, ceci peut maintenant être fait facilement en utilisant .dt pour accéder uniquement au composant de date:

df['just_date'] = df['dates'].dt.date

Ce qui précède retourne un type datetime.date, si vous voulez avoir un datetime64, vous pouvez simplement normalize le composant time à minuit pour qu'il définisse toutes les valeurs sur 00:00:00:

df['normalised_date'] = df['dates'].dt.normalize()

Cela conserve le type comme datetime64 mais l'affichage ne montre que la valeur date.

188
EdChum

Bien que j'ai voté en faveur de la réponse d'EdChum, qui est la réponse la plus directe à la question posée par l'OP, elle ne résout pas vraiment le problème de performances (elle repose toujours sur les objets python datetime, et donc toute opération sur eux ne seront pas vectorisés - c’est-à-dire que ce sera lent).

ne alternative plus performante consiste à utiliser df['dates'].dt.floor('d'). À proprement parler, il ne "garde que la partie de la date", car il règle simplement l'heure à 00:00:00. Mais cela fonctionne comme souhaité par le PO lorsque, par exemple:

  • impression à l'écran
  • enregistrer en csv
  • en utilisant la colonne pour groupby

... et c'est beaucoup plus efficace, puisque l'opération est vectorisée.

EDIT: En fait, la réponse que l'OP aurait préféré est probablement "versions récentes de pandas do non écrit le temps sur csv s'il s'agit de 00:00:00 pour toutes les observations ".

20
Pietro Battiston

Les pandas DatetimeIndex et Series ont une méthode appelée normalize qui fait exactement ce que vous voulez.

Vous pouvez en savoir plus à ce sujet dans cette réponse .

Il peut être utilisé comme ser.dt.normalize()

14
j08lue

Pandas v0.13 +: Utilisez le paramètre to_csv avec _date_format_

Évitez, dans la mesure du possible, de convertir votre série _datetime64[ns]_ en une série object dtype d'objets _datetime.date_. Ce dernier, souvent construit à l'aide de pd.Series.dt.date , est stocké sous la forme d'un tableau de pointeurs et est inefficace par rapport à une série purement basée sur NumPy.

Puisque votre problème concerne le format lors de l'écriture au format CSV , utilisez simplement le paramètre _date_format_ de _to_csv_. Par exemple:

_df.to_csv(filename, date_format='%Y-%m-%d')
_

Voir directives strftime de Python pour les conventions de formatage.

6
jpp

Solution simple:

df['date_only'] = df['date_time_column'].dt.date
5
Gil Baggio

C'est un moyen simple d'extraire la date:

import pandas as pd

d='2015-01-08 22:44:09' 
date=pd.to_datetime(d).date()
print(date)
5
Mani Abi Anand

Conversion en datetime64[D]:

df.dates.values.astype('M8[D]')

Bien que réaffecter cela à un col DataFrame le rétablisse sur [ns].

Si vous vouliez utiliser datetime.date:

dt = pd.DatetimeIndex(df.dates)
dates = np.array([datetime.date(*date_Tuple) for date_Tuple in Zip(dt.year, dt.month, dt.day)])
4
Dale Jung

Si vous avez null valeurs ou si votre colonne est de type object, cette approche m'a aidé mieux que toutes les précédentes:

df['DATE'] = pd.to_datetime(df['DATE'], errors='ignore', format='%Y%m%d')
0
Gonzalo Garcia