#python #pandas #loops #date #re
Вопрос:
У меня есть папка с сотнями файлов .xlsx, которые являются ежедневными данными многолетней давности.
Шаблон имени файла — ‘ABC DEF 20150501.xlsx’
Как я могу выбрать файлы за последний день каждого месяца за все эти годы.
К сожалению, я понятия не имею, как это сделать.
import pandas as pd
import re
files = [f for f in os.listdir(path) if re.match(r'ABC DEF [0-9] .xlsx', f)]
df = pd.DataFrame(files)
df.columns = ['file_name']
df['port_date'] = df['file_name'].apply(lambda x : x.split(' ')[3].split('.')[0])
У меня есть только дата в одной колонке, и у меня закончилась идея!
Любая помощь будет оценена по достоинству.
Комментарии:
1. У вас могут быть два файла с разными «ABC-настройками», но с одной и той же датой?
2. нет, часть «ABC DEF» исправлена. отличается только ДАТА.
3. последнее значение, если месяц означает последний календарный день, подобный
31.dec
или последний существующий день для декабря месяца для каждого года, аналогично для каждого названия месяца.4. в основном последняя дата, которая существует в каждом месяце
Ответ №1:
В следующем коде используется функция, которая добавляет день к дате, а затем сравнивает месяц новой даты с месяцем исходной даты, если они отличаются, исходная дата является последним днем месяца.
import pandas as pd
from datetime import datetime, timedelta
def last_day(to_date):
delta = timedelta(days=1)
next_day = to_date delta
if to_date.month != next_day.month:
return True
return False
# read dummy filename data
df = pd.read_csv('test.csv')
df['port_date'] = pd.to_datetime(df['file_name'].str[8:16])
df['lastday'] = df['port_date'].apply(lambda dt: last_day(dt))
Ответ №2:
Если нужна последняя строка для каждого месяца и года, извлеките даты и время, сортировку и группировку по годам и месяцам с помощью GroupBy.last
:
df = pd.DataFrame({'file_name':['ABC DEF 20150501.xlsx',
'ABC DEF 20150701.xlsx',
'ABC DEF 20150711.xlsx']})
print (df)
file_name
0 ABC DEF 20150501.xlsx
1 ABC DEF 20150701.xlsx
2 ABC DEF 20150711.xlsx
df['port_date'] = pd.to_datetime(df['file_name'].str.extract('(d ).', expand=False))
df = df.sort_values('port_date')
df = (df.groupby([df['port_date'].dt.year, df['port_date'].dt.month])
.last()
.reset_index(drop=True))
print (df)
file_name port_date
0 ABC DEF 20150501.xlsx 2015-05-01
1 ABC DEF 20150711.xlsx 2015-07-11
Ответ №3:
Объявите функцию:
def contains_date_of_last_day(name):
last_days = [
'0131',
'0228',
'0331',
'0430',
'0531',
'0630',
'0731',
'0831',
'0930',
'1031',
'1130',
'1231',
]
for i in last_days:
if i in name: return True
return False
Проверьте, содержит ли дата последнего дня, используя функцию:
files = [f for f in os.listdir(path) if contains_date_of_last_day(f)]
Комментарии:
1. У меня есть синтаксическая ошибка: внешняя функция «возврат»
2. должно сработать сейчас