Skip to content

Instantly share code, notes, and snippets.

@codertimo
Last active April 12, 2017 09:12
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save codertimo/141b2f9539f76060861973ec343b77d7 to your computer and use it in GitHub Desktop.
Save codertimo/141b2f9539f76060861973ec343b77d7 to your computer and use it in GitHub Desktop.
KMU SW17 과학과소프트웨어적사고 lab2 / n년 n월 n일로부터 n일후의 날짜는???
from datetime import datetime, timedelta
import random
'''
국민대학교 소프트웨어학과 17학번 김준성
과학과소프트웨어적사고 과제2 : n년 n월 n일로부터 n일 후의 날짜를 구하라!
'''
'''
1년 1월 1일부터 입력한 연도까지의 날짜수를 계산하는 함수힙니다
'''
def get_count(year, month, day):
# 각 월마다 몇일이 있는지 리스트로 만들어놓았다
month_list = [31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31]
# 윤년이면 2월을 29일로 바꿔줍니다.
if year % 400 == 0 or (year % 4 == 0 and year % 100 != 0):
month_list[1] = 29
# 입력받은 연도에서 1년을 빼고 시작함
year -= 1
# 1. 입력받은 연도 전까지의 날짜 수를 구합니다
# 윤년의 갯수 : year / 4 - year / 100 + year / 400
day_count = int(365 * year) + (int(year / 4) - int(year / 100) + int(year / 400))
# 2. 입력받은 월 전까지의 날짜를 구합니다
for month_index in range(0, month - 1):
day_count += month_list[month_index]
# 3. 계산한 전체 일에서 하루를 빼줍니다
day_count += day - 1
# 4. 계산된 전체 일 수를 결과값으로 넘겨줍니다
return day_count
'''
1년 1월 1일부터 n일이 지났을때 몇년몇월몇일 무슨요일인지 전달하는 함수입니다
return result 0 : year, 1 : month, 2 : day, 3 : day_type
count : 1년 1월 1일부터 몇일이 지났는지
'''
def get_day(count, korean_daytype=True):
# 초기값으로 각월마다 몇일인지, 한글로 각 요일을 리스트로 만들어줍니다
month_list = [31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31]
daytype_list = ["월요일", "화요일", "수요일", "목요일", "금요일", "토요일", "일요일"]
# 초기년도는 1년부터 시작합니다
year = 1
# 입력받은 일수에 계속 365를 빼줍니다(윤년이면 366빼기), 빼면서 1년씩 year에 더합니다
# 빼다가 남은 일수가 음수가 되면 빼주기를 그만합니다
# 이 while문으로 몇년인지 계산이 가능합니다.
while True:
if year % 400 == 0 or (year % 4 == 0 and year % 100 != 0):
if count - 366 < 0:
break
count -= 366
else:
if count - 365 < 0:
break
count -= 365
year += 1
# 초기 월은 1월부터 시작입니다.
month = 1
# 계산된 년도가 윤년이면 2월을 29일로 바꿔줍니다
if year % 400 == 0 or (year % 4 == 0 and year % 100 != 0):
month_list[1] = 29
# 남은 날짜수에 각 월에 포함된 일수를 계속 뺴줍니다, 뺄때마다 월을 1씩 증가시킵니다
# 빼다가 만약 남은일수가 음수가 되면 뺴주기를 그만합니다
while True:
if month >= 12 or count - month_list[month - 1] < 0:
break
count -= month_list[month - 1]
month += 1
# 초기일은 1일부터 시작하고, 남은 날짜를 더해줍니다
day = 1 + count
# 요일은 전체 날짜수에 7로 나누면됩니다
day_type = daytype_list[count % 7]
# 결과값으로 년 월 일 요일을 리스트로 반환합니다
if korean_daytype:
return [year, month, day, day_type]
else:
return [year, month, day, count % 7]
'''
기준일 n년 n월 n일 로부터 n일 후에 몇년 몇월 몇일이 될지 계산하는 함수입니다
year, month, day : 기준일
after : n일 후!
'''
def get_after_day(year, month, day, after):
# 1. 기준일까지의 일수를 구합니다 get_count함수가 일수를 반환해줌
basic_count = get_count(year, month, day)
# 2. n일후 + 기준일까지의 일수를 더하면 우리가 구하고자 하는 날짜의 일수가 나옵니다
basic_count += after
# 3. 몇년도 몇월 몇일 무슨요일인지 n일후 값을 get_day()에 넘겨주면 결과값을 넘겨줍니다
after_day = get_day(basic_count)
# 4. 구한 몇년도 몇월 몇일을 반환합니다
return after_day
'''
datetime 과 timedelta 모듈을 이용해서 알고리즘을 테스트 해보았습니다
각 모든 년 월 일, 이후 n일 값을 랜덤으로 받고, 실제 결과와 get_after_day()의 값을 비교하였습니다.
총 테스트 케이스를 입력받으며, 지금은 10000개의 테스트를 수행하였습니다
테스트 결과 총 테스트횟수: 10000 성공: 10000 실패: 0 정확도: 100.0
'''
def lets_test(test_count):
#맞은 갯수
correct = 0
# n번만큼 테스트 반복하기
for i in range(test_count):
random_count = random.randint(0, 100000)
random_year = random.randint(1, 2000)
random_month = random.randint(1, 12)
random_day = random.randint(1, 28)
answer = datetime(random_year, random_month, random_day) + timedelta(days=random_count)
# get_after_day에 기준일과, 몇일후를 기입하여 결과값을 받아옵니다
result = get_after_day(random_year, random_month, random_day, random_count)
if result[0] == answer.year and result[1] == answer.month and result[2] == answer.day:
correct += 1
print("[True] %d년 %d월 %d일 기준 %d일후 날짜 : %d년 %d월 %d일 %s" % (
random_year, random_month, random_day, random_count, result[0], result[1], result[2], result[3]))
else:
print("[False] %d년 %d월 %d일 기준 %d일후 날짜 : %d년 %d월 %d일 %s" % (
random_year, random_month, random_day, random_count, result[0], result[1], result[2], result[3]))
print("테스트 결과", "총 테스트횟수:", test_count, "성공:", correct, "실패:", test_count - correct, "정확도:",
float(correct / test_count * 100.00))
lets_test(10000)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment