Повторная выборка временных меток и добавление значений

#python #pandas #datetime

Вопрос:

У меня есть csv-файл с двумя столбцами. Первый столбец имеет разрешение временной метки ~5 минут, а второй столбец имеет следующие значения:

  time,values
 2021-07-30 00:00:00,0.9667
 2021-07-30 00:03:54,0.5663
 ..
 ..
 ..
 

Обратите внимание, что вторая строка занимает 3 минуты 54 секунды. Я пытаюсь точно выполнить повторную выборку столбца метки времени с разрешением 1 минута, а затем заполнить столбец значений следующим образом:

  time,values
 2021-07-30 00:00:00,0.9667
 2021-07-30 00:01:00,0.9667
 2021-07-30 00:02:00,0.9667
 2021-07-30 00:03:00,0.9667
 2021-07-30 00:04:00,0.5663
 

Мой подход

Мне удалось создать столбец с отметкой времени в одну минуту. Теперь следующий шаг-распределить значения в столбце значения в соответствии с новым разрешением метки времени. Моя идея состояла в том, чтобы взять разницу во времени между каждой строкой метки времени, сохранить результат в новом столбце, а затем добавить каждое значение в столбец значений в соответствии с результатом разницы во времени. Например, если результат разницы во времени равен 3, я бы взял первое значение в столбце значения и добавил три раза и так далее. Вот фрагмент результатов:

 time,real-power,hours_min
 0,2021-07-30 00:00:00,0.9667,0
 1,2021-07-30 00:03:54,0.5663,00:03:54
 2,2021-07-30 00:08:51,0.9887,00:04:57
 3,2021-07-30 00:13:53,0.23334,00:05:02

 

Я извлек минуты из столбца hours_min, и результат выглядит следующим образом:

 ,time,real-power,hours_min
 0,2021-07-30 00:00:00,0.9667,0.0
 1,2021-07-30 00:03:54,0.5663,3.0
 2,2021-07-30 00:08:51,0.9887,4.0
 3,2021-07-30 00:13:53,0.23334,5.0
 

Файл с отметкой времени в одну минуту содержит 1440 строк. Когда я добавил значения в столбец значения, у меня получилось 1319 значений. Позже я узнал, что проблема в том, что, когда я извлекал минуты, я не учитывал секунды, что привело к расхождениям в значениях в столбце значения.

Here’s my attempt:

 
# 2021/07/28


# The script converts 5 minutes timestamp csv file to 1 minute timestamp csv file. The timestamp resolution in the input csv file
# is not consistant. The idea is to read the minutes from the first two timestamp rows, subtract them, and the result will be the number of rows
# that will be added between the first two timestamp rows. 

# Cavaet:

# To read minutes from timestamp columns, we have to use dt accessor. The dt accessor can be used only when the timestamp column is
# datetime object like or Timestamp object like. Therefore, we will 

#################################################################################
#################################################################################
#################################################################################

import pandas as pd
from datetime import datetime
from datetime import timedelta
import numpy as np

#################################################################################
##########################  Create Timestamp Column #############################
#################################################################################


# Function creates timestamp column. 

# Credits: Stackoverflow
def create_timestamp(length):                                   # When calling this function, pass the length of the timestamp in minutes. (1 day = 1440 minutes)
    time_str = '2021-07-30 00:00:00'                                # starting date.
    date_format_str = '%Y-%m-%d %H:%M:%S'                           # timestamp format
    given_time = datetime.strptime(time_str, date_format_str)

    timestamp = []
    for length in range(0,1440):                                # length is the number of minutes in a day
        final_time = given_time   timedelta(minutes=length)
        final_time_str = final_time.strftime('%Y-%m-%d %H:%M:%S')
        timestamp.append(final_time_str)
    df = pd.DataFrame(timestamp)                                # create a dataframe for the new time stamp
    # df.to_csv("one_minute.csv")
    return df
#################################################################################
##########################          WRITE TO CSV            #####################
#################################################################################

def write_data(data,file_name):
    data.to_csv(file_name,index = False,header= False)

#################################################################################
##########################          Extract minutes         #####################
#################################################################################

def extract_minutes(df):

    df2 = pd.read_csv("data-2.csv",parse_dates=True)                # Type DataFrame

    df2['time'] = pd.to_datetime(df2['time'], errors = 'coerce')    # converted column type to datetime-like object
    
    # print(df2['time'].dtype)                                      # Double-check the type.

    df2['hours_min'] =df2['time'].diff()                            # Subtract current row from previous row and assign result in new column.

    df2['hours_min'] = df2['hours_min'].astype(str).str.split('0 days ').str[-1] # remove 0 days from hour_min column


    df2['hours_min'] = pd.to_datetime(df2['hours_min'])



    df2['hours_min'] = df2['hours_min'].dt.minute.fillna(0)                     # Get only minutes and convert NaN values to zeroes.
    
    # df2['hours_min'] = pd.to_datetime(df2['hours_min'])

    # df2['hours_min'] = df2['hours_min'].dt.minute.fillna(0)

    df2.to_csv('check_minutes.csv')

    return df2
#################################################################################
#######     repeat power values to match new timestamp resolution       #########
#################################################################################

def read_power_vals(df,df2):
    new_pow_values = []

    # df2.set_index(['time'])['real-power'].repeat(df['hours_min'].astype(int)).reset_index()
    # df2['hours_min'].astype(int)
    # print(df2['real-power'].repeat(df2['hours_min']).reset_index())
    

    # print(df.iloc[:10])
    # print(df2)
    # dff = pd.DataFrame(np.repeat(df2['real-power'].values,3,axis=0))
    # print(dff)


    # print(df2)
    # p_vals = df2['real-power'].to_list()
    
    # minutes = df2['hours_min'].to_list()  

    # counter = 0

    # for i,k in zip(p_vals,minutes):
    #   # print(i,k)
    #   new_pow_values.append(i)
        
    #   print(f'this is counter {counter}.n This is i {i}n And this is k {k}n This is the array {new_pow_values}n')
        
    #   # counter = counter   1

    #   if counter == k:
    #       i = i   1
    #       # k = k   1
    #       counter = 0
    #   else:
    #       new_pow_values.append(i)
    #       counter = counter   1
    # if counter == 5:
    #   break
    # print(p_vals,len(p_vals))
    # print(minutes,len(minutes))
    

    # product = []
    # j = 0
    # for i in minutes:
    #   product.extend(int(i) * [p_vals[j]])
    #   # print(int(i) * [p_vals[j]], "should be of length: ",int(i))

    #   j =1

        # print(product,len(product))
    # print(minutes[-10:])
    # print(len(product))
    # print(len(df))
    # print(len(new_pow_values))





x = create_timestamp(1440)
# write_data(x,'trial.csv')

y = extract_minutes(x)

z = read_power_vals(x,y)

 

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

Спасибо всем.