Приведение даты в CSV для Pandas и ошибка вывода - PullRequest
0 голосов
/ 13 января 2019

Я полагаю, что это может быть результатом устаревшей ошибки, но я не смог выделить источник проблемы.

Окружающая среда:
- Python 2.7
- панды 0.19.1

Проблема

Использование панд для чтения / обработки / записи данных CSV приводит к редким ошибкам в выводе.

Пример данных

csv_data = """ timestamp,outdoor temperature 2019-01-10 07:16:38.758659,17.5 2019-01-10 07:31:51.449437,16.9 2019-01-10 07:47:04.458140,17.5 2019-01-10 08:02:17.372576,17.8 2019-01-10 08:17:30.156140,18.3 2019-01-10 08:32:42.878982,19.2 2019-01-10 08:47:55.782450,19.9 2019-01-10 09:03:08.907534,21.0 2019-01-10 09:18:21.599587,21.3 2019-01-10 09:33:34.572015,21.8 2019-01-10 09:48:47.524057,22.5 2019-01-10 10:04:00.420671,23.3 2019-01-10 10:19:13.187784,24.2 2019-01-10 10:34:26.118712,24.2 2019-01-10 10:49:39.000694,24.5 2019-01-10 11:04:51.870451,25.6 2019-01-10 11:20:04.763880,26.0 2019-01-10 11:35:17.541427,26.4 2019-01-10 11:50:30.252781,27.1 """

Пример кода

Ядро ввода-вывода и код обработки (содержит одну или две строки, которые, я не думаю, имеют отношение к проблеме, но включены для полноты)

#! /usr/bin/env python
# -*- coding: utf-8 -*-

import datetime as dt
import pandas as pd


# Load the entire CSV
df = pd.read_csv(full_path, delimiter=',', encoding='utf-8')

# Coerce column 0 name
df.columns = [c.lower() if c == 'Timestamp' else c for c in df.columns]
column_names = list(df)

# Convert column 0 to datetime
df[column_names[0]] = pd.to_datetime(df[column_names[0]], errors='coerce', format="%Y-%m-%d %H:%M:%S.%f").astype(dt.datetime)

# Drop obs older than delta hours
cut_off = dt.datetime.now() - dt.timedelta(hours=72)
df = df[df[column_names[0]] >= cut_off]

# Add a new observation to the end of the dataframe
df = df.append({column_names[0]: dt.datetime.now(), column_names[1]: '12.3'}, ignore_index=True)

# Keep max 300 obs
df = df.tail(300)

# Replace the CSV with the revised dataframe
df.to_csv(full_path, sep=',', encoding='utf-8', index=False)

Пример вывода

Иногда будет приводить к такому выводу (который включает в себя то, что представляется частями строки эпохи POSIX, добавленной к наблюдению в столбце 1):
timestamp,outdoor temperature 2019-01-10 07:16:38.758659,17.5 2019-01-10 07:31:51.449437,16.9 2019-01-10 07:47:04.458140,17.5 2019-01-10 08:02:17.372576,17.8 2019-01-10 08:17:30.156140,18.3-01-01 00:00:00 2019-01-10 08:32:42.878982,19.2 2019-01-10 08:47:55.782450,19.9 2019-01-10 09:03:08.907534,21.0 2019-01-10 09:18:21.599587,21.3 2019-01-10 09:33:34.572015,21.8 2019-01-10 09:48:47.524057,22.5 2019-01-10 10:04:00.420671,23.3 2019-01-10 10:19:13.187784,24.2-01-01 00:00:00 2019-01-10 10:34:26.118712,24.2 2019-01-10 10:49:39.000694,24.5 2019-01-10 11:04:51.870451,25.6 2019-01-10 11:20:04.763880,26.0 2019-01-10 11:35:17.541427,26.4 2019-01-10 11:50:30.252781,27.1

Я пытался использовать .append() и .extend() и различные комбинации кодирования / декодирования, но я обнаружил, что эта ошибка очень противоречива и трудна для воспроизведения. Сначала я подозревал, что это может быть результатом расширенных символов Unicode или расы, но я считаю, что я исключил обе эти возможности. Если код Python не является виновником, я могу исправить библиотеку pandas (но не обновить ее до более новой версии) и должен остаться на Python 2.7.

Я хочу избежать атаки методом грубой силы, при которой я просто перебираю столбец 1 obs и отбрасываю бит зла. Любые предложения будут наиболее ценными. Заранее спасибо.

Обновление 1

Дополнительные исследования показывают, что .astype() может время от времени расстраиваться и в сочетании с errors='coerce' может маскировать проблему. Будет ли какая-либо добавленная стоимость с использованием какой-либо другой формы преобразования даты, например:

df[column_names[0]] = [dateutil.parser.parse(obs) for obs in df[column_names[0]]]
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...