So, i have this dictionary:
days_per_month = {"01": 31, "02": 28,
"03": 31, "04": 30,
"05": 31, "06": 30,
"07": 31, "08": 31,
"09": 30, "10": 31,
"11": 30, "12": 31}
And this function:
def add_months(month):
"""
If needed, increment one day and check other parameters, such as months and years.
Requires:
- dmy str with a date represented as DD:MM:YY.
Ensures: str with the updated date represented as DD:MM:YY.
"""
if month == 2:
day = get_days(dmy)
if check_year(year) == "True":
if day > 29:
month += 1
day = 1
else:
if day > 28:
month += 1
day = 1
if days_per_month[month] = 31:
day = get_days(dmy)
if day > 31:
month += 1
day = 1
if days_per_month[month] = 30:
day = get_days(dmy)
if day > 30:
month += 1
day = 1
return month
Function get_days:
def get_days(dmy):
"""Get the number of days from a DD:MM:YY date representation.
Requires: dmy str with a date represented as DD:MM:YY.
Ensures: int with the number of days
"""
return int(dmy.split(':')[0])
Function check_year:
def check_year(year):
"""
Checks if the current year is a leap year or not.
Requires: year str with the year.
Ensures: 'True' if year is leap year; 'False' if year isn't a leap year.
"""
return year % 4 == 0 and (year % 100 != 0 or year % 400 == 0)
Here is what I'm trying to do: I have a previous function where I increment x minutes to a certain time, let's call it y. Imagine that y = "23:56" and x = "5", 23:56 + 5 = 24:01. So, I have another function that increments one day on the date when this happens.
Now I'm trying to finish my function that changes THE MONTH. For example:
y = 23:56 and x = 5, == 24:01. However the previous date was 31/12, and now it is 32/12: I incremented a day with my previous function, but now I have to also change the month with my function add_months. So, I check my days_per_month dictionary and try to find the month(the key in the dictionary)'s value, so I can have the max number of days of that month. I think that's how I'm supposed to do it, but I keep getting this error:
if days_per_month[month] = 31:
SyntaxError: invalid syntax
if days_per_month[month] = 30:
SyntaxError: invalid syntax
What am I doing wrong?
Obs1 - python 3.2
Obs2 - if you have any suggestion to improve any of my functions, please tell me!
your basic problem is that you try to assign a value and not to compare it. use
if days_per_month[month] == 31: instead of if days_per_month[month] = 31:
However i would suggest using datetime like this:
from datetime import *
a=datetime(2017,2,28,23,56,00)
b=a+timedelta(minutes=5)
what I do is initialize a with the Date 28.02.2017 23:56:00 and then add 5 minutes to this datetime and get the Date 01.03.2017 00:01:00 in b
Related
Create a calendar program that allows the user to enter a day, month, and year in three separate variables as shown below.
Please enter a date
Day:
Month:
Year:
Then, ask the user to select from a menu of choices using this formatting:
Menu:
1) Calculate the number of days in the given month.
2) Calculate the number of days left in the given year.
The program must include the following functions:
leap_year: Takes the year as a parameter and returns 1 if a year is a leap year
(Links to an external site.)
and 0 if it is not. This information will only be used by other functions.
number_of_days: This subprogram will accept two parameters in the following order: month and year. It will return how many days are in the given month
(Links to an external site.)
.
daysunderscoreleft: This will accept three parameters in the following order: day, month, and year. It should calculate the number of days left in the year, and return the value of number of days left. This should not include the date the user entered in the count.
def is_leap_year(year):
return (year % 4 == 0) and (year % 100 != 0) or (year % 400 == 0)
def days_in_month(month, year):
if month in ['September', 'April', 'June', 'November']:
print("30")
elif month in ['January', 'March', 'May', 'July', 'August','October','December']:
print("31")
elif month == 'February' and is_leap_year(year) == True:
print("29")
elif month == 'February' and is_leap_year(year) == False:
print("28")
else:
return None
print("Please enter a date: ")
x = int(input("Day: "))
y = str(input("Month: "))
z = str(input("Year: "))
print("Menu:")
o = int(input("1) Calculate the number of day in the given month. \n2) Calculate the number of days left in the given year. "))
if(o == "2"):
print (days_in_month(y,z))
This is what I have so far. I am kind of confused on how to find the number of days left in a month and year and I just need help with that. Sorry for the messy format, I didn't know how to format it correctly.
Can you try the following:
def is_leap_year(year):
return (year % 4 == 0) and (year % 100 != 0) or (year % 400 == 0)
def days_in_month(day, month, year):
if month in ['September', 'April', 'June', 'November']:
return 30 - day
elif month in ['January', 'March', 'May', 'July', 'August','October','December']:
return 31 - day
elif month == 'February' and is_leap_year(year) == True:
return 29 - day
elif month == 'February' and is_leap_year(year) == False:
return 28 - day
else:
return None
print("Please enter a date: ")
x = int(input("Day: "))
y = str(input("Month: "))
z = int(input("Year: "))
print("Menu:")
o = int(input("1) Calculate the number of day in the given month. \n2) Calculate the number of days left in the given year.\n"))
if(o == 1):
print (days_in_month(x, y,z))
It will give you the days left in month.
Output:
Please enter a date:
Day: 15
Month: February
Year: 2020
Menu:
1) Calculate the number of day in the given month.
2) Calculate the number of days left in the given year.
1
14
Will it be okay to find the days left in year using any python library, then i can do it..
if month == 12:
if 0 < date < 23:
return 'SAG'
if 23 <= date < 32:
return 'CAP'
if month == 1:
if 0 < date < 21:
return 'CAP'
if 21 <= date < 32:
return 'AQU'
if month == 2:
if 0 < date < 20:
return 'AQU'
if 20 <= date < 30:
return 'PIS'
if month == 3:
if 0 < date < 21:
return 'PIS'
if 21 <= date < 32:
return 'ARI'
I am looking for a simpler and more effective way of completing my function of finding astrological sign according to month and date, is there a more effective method or is using 12 if loops a must?
You're right to think there's a better way. Use the datetime package. Set up a list of start dates and check the appropriate range for the given date. Since Capricorn spans the calendar year, you'll have two entries for that one:
import datetime
from datetime import date
signs = [ # start date, abbreviation
(date(month=1, day=1), "CAP"),
(date(month=1, day=20), "AQU"),
(date(month=2, day=18), "PIC"),
...
(date(month=12, day=19), "CAP"),
(date(month=12, day=31), "end of year"),
]
Now, you build a date from the given month and year. Iterate through the list, looking for the a given date being greater than the current date, and less than the next one. When you find that entry, you report/return the sign abbreviation.
Does that get you moving?
Dates are always tough to work with and mapping the lunar calendar to the solar calendar present special problems. It becomes easier if you approach it from a days in the year problem instead of a dates problem.
import numpy as np
from datetime import datetime as dt
def getSign(birthDate):
#get day of year of birth
dayOfBirth = (birthDate - dt(birthDate.year, 1, 1)).days
#adjust for leap years
if birthDate.year%4==0 and dayOfBirth > 60:
dayOfBirth -= 1
#build dict of max day for each sign. capricorn is set twice due to straddling of solar year
signs = {20:'Capricorn', 49:'Aquarius', 79:'Pisces', 109:'Aries', 140:'Taurus', 171:'Genini', 203:'Cancer', 234:'Leo', 265:'Virgo', 295:'Libra', 325:'Scorpio', 355:'Sagitarius', 365:'Capricorn'}
#create numpy array of maximum days
daysArray = np.array(list(signs.keys()))
#get sign max days closest to but larger than dayOfBirth
maxDayCount = min(daysArray[daysArray >= dayOfBirth])
return signs[maxDayCount]
>>> getSign(dt(2000, 3, 22))
'Aries'
>>> getSign(dt(2000, 1, 1))
'Capricorn'
>>> getSign(dt(2000, 12, 22))
'Sagitarius'
>>> getSign(dt(2000, 12, 31))
'Capricorn'
I'm trying to build a function that recieves a date and adds days, updating everything in case it changes, so far i've come up with this:
def addnewDate(date, numberOfDays):
date = date.split(":")
day = int(date[0])
month = int(date[1])
year = int(date[2])
new_days = 0
l = 0
l1 = 28
l2 = 30
l3 = 31
#l's are the accordingly days of the month
while numberOfDays > l:
numberOfDays = numberOfDays - l
if month != 12:
month += 1
else:
month = 1
year += 1
if month in [1, 3, 5, 7, 8, 10, 12]:
l = l3
elif month in [4, 6, 9, 11]:
l = l2
else:
l = l1
return str(day) + ':' + str(month) + ':' + str(year) #i'll deal
#with fact that it doesn't put the 0's in the < 10 digits later
Desired output:
addnewDate('29:12:2016', 5):
'03:01:2017'
I think the problem is with either the variables, or the position i'm using them in, kinda lost though..
Thanks in advance!
p.s I can't use python build in functions :)
Since you cannot use standard library, here's my attempt. I hope I did not forget anything.
define a table for month lengths
tweak it if leap year detected (every 4 year, but special cases)
work on zero-indexed days & months, much easier
add the number of days. If lesser that current month number of days, end, else, substract current month number of days and retry (while loop)
when last month reached, increase year
add 1 to day and month in the end
code:
def addnewDate(date, numberOfDays):
month_days = [31,28,31,30,31,30,31,31,30,31,30,31]
date = date.split(":")
day = int(date[0])-1
month = int(date[1])-1
year = int(date[2])
if year%4==0 and year%400!=0:
month_days[1]+=1
new_days = 0
#l's are the accordingly days of the month
day += numberOfDays
nb_days_month = month_days[month]
done = False # since you don't want to use break, let's create a flag
while not done:
nb_days_month = month_days[month]
if day < nb_days_month:
done = True
else:
day -= nb_days_month
month += 1
if month==12:
year += 1
month = 0
return "{:02}:{:02}:{:04}".format(day+1,month+1,year)
test (may be not exhaustive):
for i in ("28:02:2000","28:02:2004","28:02:2005","31:12:2012","03:02:2015"):
print(addnewDate(i,2))
print(addnewDate(i,31))
result:
02:03:2000
31:03:2000
01:03:2004
30:03:2004
02:03:2005
31:03:2005
02:01:2013
31:01:2013
05:02:2015
06:03:2015
of course, this is just for fun. Else use time or datetime modules!
I wrote a program to calculate the number of days between two dates and it works fine except for one case. If I want to calculate the number of days between two dates and the end date is in February the number of days is not correct (exactly three days are missing)
Example:
Date 1: 2012,1,1
Date 2: 2012,2,28
Program returns 55 days (should be 58)
I guess there is an issue with the leap days but I don't get why this does not cause any wrong values for any other two dates and why the difference between the correct value and the value of my program is 3 days. My code example which should work as is can be found below. Any advice is appreciated.
daysOfMonths = [ 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31]
# Count the number of leap years
def countLeapYears(year, month):
if month <= 2:
year = year - 1
return int(year/4 - year/100 + year/400 )
# Determine the number of days between 0/00/0000 and the two dates and calculate the difference
def daysBetweenDates(year1, month1, day1, year2, month2, day2):
days = 0
n1 = year1 * 365 + day1
for month in range (0, month1):
n1 += daysOfMonths[month]
n1 += countLeapYears(year1, month1)
n2 = year2 * 365 + day2
for month in range (0, month2):
n2 += daysOfMonths[month]
n2 += countLeapYears(year2, month2)
return n2 - n1
def test():
test_cases = [((2012,1,1,2012,2,28), 58),
((2011,6,30,2012,6,30), 366),
((2011,1,1,2012,8,8), 585 ),
((1900,1,1,1999,12,31), 36523)]
for (args, answer) in test_cases:
result = daysBetweenDates(*args)
if result != answer:
print "Test with data:", args, "failed"
else:
print "Test case passed!"
test()
You have an off-by-one error in these lines:
for month in range (0, month1):
...
for month in range (0, month2):
Lists are zero-indexed in Python, but months are one-indexed in your program. So the proper code is:
for month in range (month1 - 1)
...
for month in range (month2 - 1)
I am trying to output 1 to 30 days but it isn't working and it says Your code didn't display any output
here is my code:
def nextDay(year, month, day):
day = 0
while (day < 30):
day = day + 1
print day
this what they are having me do. But i am stuck on the day portion. Sorry i noticed I put month instead of day so i fixed it, but this is what I am trying to get to at the end.
Define a simple nextDay procedure, that assumes every month has 30 days.
For example:
nextDay(1999, 12, 30) => (2000, 1, 1)
nextDay(2013, 1, 30) => (2013, 2, 1)
nextDay(2012, 12, 30) => (2013, 1, 1) (even though December really has 31 days)
def nextDay(year, month, day):
"""
Returns the year, month, day of the next day.
Simple version: assume every month has 30 days.
"""
# YOUR CODE HERE
return
Well if you're trying to output 1 through 30 this will work...
for x in range(1, 31):
print 'Day: %d' % x
I literally don't get your function at all, as it makes no sense.
In addition, I don't really get why you would use a while loop for that as it is slower than both range and xrange.
Did you want this
def nextDay(year, month, day):
if day == 30:
if month == 12:
day, month = 1, 1
year+=1
else:
month+=1
else:
day+=1
return (year, month, day)
>>>nextDay(2012, 12, 30)
(2013, 1, 1)
I hope this is what you needed.
def nextDay(year, month, day):
day += 1
if day > 30:
day = 1
month += 1
if month > 12:
month = 1
year += 1
return (year, month, day)
Your code did not show anything as I don't think you have called the function.