2010-04-08 2 views
203

Как узнать, какой номер недели текущий год 16 июня (wk24) с Python?Как получить номер недели в Python?

+1

@Donal: Один смотрит на 16 июня, другой на 26 июня – interjay

+4

Определить неделя 1. isocalendar() не единственный способ сделать это. –

+1

Обратите внимание, что вывод 'strftime ("% U ", d)' может отличаться от 'isocalendar()'. Например, если вы измените год на 2004 год, вы получите 24 неделю, используя 'strftime()' и 25 неделю, используя 'isocalendar()'. – moooeeeep

ответ

254

datetime.date имеет isocalendar() метод, который возвращает кортеж, содержащий календарную неделю:

>>> datetime.date(2010, 6, 16).isocalendar()[1] 
24 

datetime.date.isocalendar() является экземпляром-метод возвращает кортеж, содержащий год, НомерНедели и день недели в соответствующем порядке для данного экземпляра даты.

+5

Это поможет, если вы объяснили «[1]» или указали, где искать информацию. –

+2

Я думаю, что самый простой - извлечь номер недели, используя strftime, best import datetime today = datetime.now() week = today.strftime ("% W") – bipsa

+6

Немного поздно. Но на моей машине 'date (2010, 1, 1) .isocalendar() [1]' возвращает '53'.Из документов: «Например, 2004 год начинается в четверг, поэтому первая неделя ISO 2004 года начинается в понедельник, 29 декабря 2003 года и заканчивается в воскресенье, 4 января 2004 года, так что« дата (2003, 12, 29)) .isocalendar() == (2004, 1, 1) 'и' date (2004, 1, 4) .isocalendar() == (2004, 1, 7) '." – jclancy

60

Я считаю, что date.isocalendar() будет ответом. This article объясняет математику за календарем ISO 8601. Ознакомьтесь с частью date.isocalendar() в datetime page документации Python.

>>> dt = datetime.date(2010, 6, 16) 
>>> wk = dt.isocalendar()[1] 
24 

.isocalendar() возвращает 3-кортеж (год, неделя NUM, WK день). dt.isocalendar()[0] возвращает год, dt.isocalendar()[1] возвращает номер недели, dt.isocalendar()[2] возвращается неделя день. Просто, как может быть.

+2

+1 для ссылки, которая объясняет неинтуитивный характер недель ИСО. –

25

Вот еще один вариант:

import time 
from time import gmtime, strftime 
d = time.strptime("16 Jun 2010", "%d %b %Y") 
print(strftime("%U", d)) 

который печатает 24.

См: http://docs.python.org/library/datetime.html#strftime-and-strptime-behavior

+1

+1 для URL дополнительной информации –

+7

или% W, если ваши недели начинаются по понедельникам. – ZeWaren

+0

Этот подход лучше в тех случаях, когда вы не хотите разбивать или конвертировать дату, которая приходит как строка ... просто передайте строку в strptime в строчном формате, как есть, и укажите формат во втором аргументе. Хорошее решение. Помните:% W, если неделя начинается по понедельникам. – MANU

13

Неделя ISO предложил другим является хорошим, но это не может соответствовать вашим потребностям. Предполагается, что каждая неделя начинается с понедельника, что приводит к некоторым интересным аномалиям в начале и конце года.

Если вы хотели бы использовать определение, которое говорит неделя 1 всегда 1 января по 7 января, независимо от дня недели, используйте вывод так:

>>> testdate=datetime.datetime(2010,6,16) 
>>> print(((testdate - datetime.datetime(testdate.year,1,1)).days // 7) + 1) 
24 
+1

Сказать, что isocalendar имеет «некоторые интересные аномалии» на начала и конца года, кажется, немного преуменьшает. Результаты isocalendar очень вводят в заблуждение (даже если они действительно не соответствуют требованиям ISO) для некоторых значений даты и времени, например, 29 декабря 2014 года, 00:00:00, которые согласно isocalendar имеют значение года 2015 и неделю Число 1 (см. моя запись ниже). – Kevin

+3

@ Кевин, это не так, просто их определения не соответствуют вашим. ISO решил две вещи: сначала, что вся неделя с понедельника по воскресенье будет в том же году, во-вторых, что год, содержащий большую часть дней, будет назначаться. Это приводит к дням недели вокруг начала и конца года, которые переходят в соседний год. –

+4

Согласовано. Но по определению большинства людей, 29 декабря 2014 года, определенно, не будет 1-й недели 2015 года. Я просто хотел привлечь внимание к этому потенциальному источнику смятения. – Kevin

15

Как правило, чтобы получить ток номер недели (начинается с воскресенья):

from datetime import * 
today = datetime.today() 
print today.strftime("%U") 
+4

Из документации strftime ('% U'): «Номер недели года (воскресенье в качестве первого дня недели) в виде десятичного числа [00,53]. Все дни в новом году, предшествующем первому воскресенью, считается на неделе 0. " –

2

isocalendar() возвращает некорректные год и НомерНедели значения для некоторых дат:

Python 2.7.3 (default, Feb 27 2014, 19:58:35) 
[GCC 4.6.3] on linux2 
Type "help", "copyright", "credits" or "license" for more information. 
>>> import datetime as dt 
>>> myDateTime = dt.datetime.strptime("20141229T000000.000Z",'%Y%m%dT%H%M%S.%fZ') 
>>> yr,weekNumber,weekDay = myDateTime.isocalendar() 
>>> print "Year is " + str(yr) + ", weekNumber is " + str(weekNumber) 
Year is 2015, weekNumber is 1 

Сравните с подходом Марка Ransom в:

>>> yr = myDateTime.year 
>>> weekNumber = ((myDateTime - dt.datetime(yr,1,1)).days/7) + 1 
>>> print "Year is " + str(yr) + ", weekNumber is " + str(weekNumber) 
Year is 2014, weekNumber is 52 
+2

Рассматривая некоторые ссылки о календаре iso8601 (например, http://www.staff.science.uu.nl/~gent0113/calendar/isocalendar.htm), я вижу, что значения year и weeknumber, возвращаемые isocalendar(), являются не «неправильно» как таковой. В соответствии с ISO8601, например, 2004 год начался 29 декабря 2003 года. Таким образом, isocalendar() может быть правильным в возвращении 2015 года для 29 декабря 2014 года, но для многих целей людей это будет довольно вводящим в заблуждение , – Kevin

45

Вы можете получить номер недели непосредственно из DateTime в строку.

>>> import datetime 
>>> datetime.date(2010, 6, 16).strftime("%V") 
'24' 

Также вы можете получить Diferent «тип» неделю числа года меняющегося параметр STRFTIME для:

% U - номер недели текущего года, начиная с первым воскресеньем как первый день первой недели.

% V - ISO-8601 номер недели текущего года (от 01 до 53), где недели 1 является первой неделей, что имеют, по меньшей мере, 4 дней в текущем году, и понедельник, как первый день неделя.

% W - номер недели текущего года, начиная с первого понедельника в качестве первого дня первой недели.

У меня его есть от here. Он работал для меня в Python 2.7.6

+0

Что вы цитируете, какое-то руководство для Linux? Python 2.7.5 и 3.3.2 говорят 'Invalid format string' для этого шаблона. В их документах также не упоминается '% V'. –

+2

Извините, я не упоминал об этом, у меня есть [здесь] (http://www.tutorialspoint.com/python/time_strftime.htm). Это сработало для меня в Python 2.7.6. – jotacor

12

Для целочисленного значения мгновенной недели года попытки:

import datetime 
datetime.datetime.utcnow().isocalendar()[1] 
8

Если вы используете только isocalendar номер недели по всем направлениям следующее должно быть достаточно :

import datetime 
week = date(year=2014, month=1, day=1).isocalendar()[1] 

Это извлекает второй член кортежа, возвращенный isocalendar для нашего номера недели.

Однако, если вы собираетесь использовать функции даты, которые имеют дело с григорианским календарем, isocalendar не будет работать! Рассмотрим следующий пример:

import datetime 
date = datetime.datetime.strptime("2014-1-1", "%Y-%W-%w") 
week = date.isocalendar()[1] 

Строка здесь говорит, чтобы вернуть понедельник первой недели в 2014 году, как наш сегодняшний день. Когда мы используем isocalendar для получения номера недели здесь, мы ожидаем получить тот же номер недели назад, но мы этого не сделаем. Вместо этого мы получаем недельный номер 2. Почему?

Неделя 1 в григорианском календаре является первой неделей, содержащей понедельник. Неделя 1 в isocalendar - первая неделя, содержащая четверг. Частичная неделя в начале 2014 года содержит четверг, так что это неделя 1 по isocalendar и делает date неделю 2.

Если мы хотим получить григорианскую неделю, нам нужно будет преобразовать из isocalendar в григорианский. Вот простая функция, которая делает трюк.

import datetime 

def gregorian_week(date): 
    # The isocalendar week for this date 
    iso_week = date.isocalendar()[1] 

    # The baseline Gregorian date for the beginning of our date's year 
    base_greg = datetime.datetime.strptime('%d-1-1' % date.year, "%Y-%W-%w") 

    # If the isocalendar week for this date is not 1, we need to 
    # decrement the iso_week by 1 to get the Gregorian week number 
    return iso_week if base_greg.isocalendar()[1] == 1 else iso_week - 1 
0
userInput = input ("Please enter project deadline date (dd/mm/yyyy/): ") 

import datetime 

currentDate = datetime.datetime.today() 

testVar = datetime.datetime.strptime(userInput ,"%d/%b/%Y").date() 

remainDays = testVar - currentDate.date() 

remainWeeks = (remainDays.days/7.0) + 1 


print ("Please pay attention for deadline of project X in days and weeks are : " ,(remainDays) , "and" ,(remainWeeks) , "Weeks ,\nSo hurryup.............!!!") 
6

Вы можете попробовать% директиву W, как показано ниже:

d = datetime.datetime.strptime('2016-06-16','%Y-%m-%d') 
print(datetime.datetime.strftime(d,'%W')) 

'% W': Номер недели года (понедельник, как первый день недели) как десятичное число , Все дни в новом году, предшествующий первому воскресенью, считаются относящимися к неделе 0. (00, 01, ..., 53)

2

я подвести итоги дискуссии двух этапов:

  1. Преобразовать сырье формат до объекта datetime.
  2. Используйте функцию объекта datetime или объект date, чтобы рассчитать номер недели.

Разминка

`` `питон

from datetime import datetime, date, time 
d = date(2005, 7, 14) 
t = time(12, 30) 
dt = datetime.combine(d, t) 
print(dt) 

` ``

первый шаг

Чтобы вручную сгенерировать datetime объект, мы можем использовать datetime.datetime(2017,5,3) или datetime.datetime.now().

Но в действительности мы обычно должны разбирать существующую строку. мы можем использовать функцию strptime, такую ​​как datetime.strptime('2017-5-3','%Y-%m-%d'), в которой вы должны указать конкретный формат. Деталь кода другого формата можно найти в official documentation.

В качестве альтернативы, более удобным способом является использование модуля dateparse. Примерами являются dateparser.parse('16 Jun 2010'), dateparser.parse('12/2/12') или dateparser.parse('2017-5-3')

Приведенные выше два подхода возвращают объект datetime.

второй этап

Используйте полученную datetime объект для вызова strptime(format). Например,

`` `питона

dt = datetime.strptime('2017-01-1','%Y-%m-%d') # return a datetime object. This day is Sunday 
print(dt.strftime("%W")) # '00' Monday as the 1st day of the week. All days in a new year preceding the 1st Monday are considered to be in week 0. 
print(dt.strftime("%U")) # '01' Sunday as the 1st day of the week. All days in a new year preceding the 1st Sunday are considered to be in week 0. 
print(dt.strftime("%V")) # '52' Monday as the 1st day of the week. Week 01 is the week containing Jan 4. 

` ``

Это очень сложно решить, какой формат использовать. Лучше всего получить объект date для вызова isocalendar(). Например,

`` `питона

dt = datetime.strptime('2017-01-1','%Y-%m-%d') # return a datetime object 
d = dt.date() # convert to a date object. equivalent to d = date(2017,1,1), but date.strptime() don't have the parse function 
year, week, weekday = d.isocalendar() 
print(year, week, weekday) # (2016,52,7) in the ISO standard 

` ``

В действительности, вы будете более склонны использовать date.isocalendar() подготовить еженедельный отчет, особенно в «Рождество-Новый год «сезон покупок.

2

Для сегодняшнего дня:

import datetime as date 
weeknumber = date.today().isocalendar()[1] 
Смежные вопросы