프로그래머스 | 2022 KAKAO BLIND RECRUITMENT | 주차 요금 계산 | Python

kimminjunnn·2025년 10월 22일

알고리즘

목록 보기
211/311

문제 링크 :https://school.programmers.co.kr/learn/courses/30/lessons/92341

문제 파악

주차 요금을 계산하려고 한다.

표의 흐름을 따라가보면

기본 시간은 180분, 기본요금 5,000원
그리고 180분이 지난 시간부터 10분마다 600원의 할증이 붙는 것 같다.


<차량들의 입,출차 기록이다.>

몇시 몇분에 어떤 차량이 입차했는지, 출차했는 지를 알려주고 있다.


< 주차요금 계산법과 몇가지 규칙들이 적혀있다.>

0000번 부터 보면 이 차는 위 입/출차 기록을 보면 6:00~6:34 주차하였고, 추가로 18:59 입차하여 출차 기록이 없다.

입차했는데 출차 기록이 없다면 당일 23:59에 출차한 것으로 간주한다고 규칙에 적혀있다.

그래서 0000은 34분 + 5시간 해서 총 334분 주차하였다.

주차 요금은 아까 예상한 것과 동일하게 매겨진다.

기본요금 + 초과한 시간당 단위시간당 요금으로.
단 초과한 시간이 단위시간으로 나누어 떨어지지 않으면, 올림한댄다.
즉 1분만 초과해도 단위시간으로 올라간다.

그래서 0000은 기본요금 5천원 + |(334- 기본시간 180) / 10|올림 x 600 = 14600 을 내야 한댄다.

친절하게 계산법까지 알려주었다.

계산법은

기본요금 +
(총 주차 시간 - 기본 시간) / 단위시간 을 올림한 값에
x 단위시간당 요금해주면 계산된다.


<입출력 예>

주차요금과 시간에 관련된 fees와 입/출차 관련 기록인 records가 주어진다.

fees 는 [기본 시간(분), 기본 요금(원), 단위 시간(분), 단위 요금(원] 배열로 주어진다.

records는 [입/출차 시간, 차량 번호, 입차인지 출차인지] 로 배열로 주어진다.


<제한사항>

제한 사항중 특이사항으로는

  • records의 원소들은 시각을 기준으로 오름차순으로 정렬되어 주어집니다.
  • 오류가 날법한 입력은 주어지지 않는다.

정도가 있는 것 같다.


결국에 입/출차 기록이 있는 차량들에 주차요금을 차량 번호가 작은 자동차부터 배열에 담아 return 하면 된다.


해답 및풀이

from collections import defaultdict 
import math


def to_minutes(hhmm):
    h, m = map(int, hhmm.split(':'))
    return h * 60 + m

def solution(fees, records):
    records_dict = defaultdict(list) # {차량번호 : [(입/출차 시간,IN or OUT), (입/출차 시간,IN or OUT)], 차량번호 : [ ... ] }

    for r in records:
        time, number, INorOUT = r.split(" ")
        records_dict[number].append([time,INorOUT])
    # records_dict = {'5961': [['05:34', 'IN'], ['07:59', 'OUT'], ['22:59', 'IN'], ['23:00', 'OUT']], '0000': [['06:00', 'IN'], ['06:34', 'OUT'], ['18:59', 'IN']], '0148': [['07:59', 'IN'], ['19:09', 'OUT']]})

    
    # 내가 원하는 것, sorted_cars 순서대로 record_dict에 value들이 들어오는 것
    sorted_cars_record = []
    for k in sorted(records_dict):
        sorted_cars_record.append(records_dict[k])
    #  sorted_cars_record = [[['06:00', 'IN'], ['06:34', 'OUT'], ['18:59', 'IN']], [['07:59', 'IN'], ['19:09', 'OUT']] , [['05:34', 'IN'], ['07:59', 'OUT'], ['22:59', 'IN'], ['23:00', 'OUT']]]

    # IN만 있고 OUT이 없으면 ['23:59','OUT'] 을 추가 해주기
    addition = ['23:59', 'OUT']
    for record in sorted_cars_record:
        if len(record) % 2 == 1:
            record.append(addition)
    # sorted_cars_record = [[['06:00', 'IN'], ['06:34', 'OUT'], ['18:59', 'IN'], ['23:59', 'OUT']], [['07:59', 'IN'], ['19:09', 'OUT']], [['05:34', 'IN'], ['07:59', 'OUT'], ['22:59', 'IN'], ['23:00', 'OUT']]]

    result = []

    for sorted_car_record in sorted_cars_record:
        total_time = 0
        for i in range(0,len(sorted_car_record), 2): # 쌍 마다 분 단위 차이를 누적.
            tin, _ = sorted_car_record[i]
            tout, _ = sorted_car_record[i+1]
            total_time += to_minutes(tout) - to_minutes(tin)

        if total_time <= fees[0]:
            fee = fees[1] # 기본 요금이면 기본요금만

        else:
            over = total_time - fees[0]
            units = math.ceil(over / fees[2])
            fee = fees[1] + units * fees[3]    
        
        result.append(fee)
    

    return result

for i in range(0,len(sorted_car_record), 2): # 쌍 마다 분 단위 차이를 누적.
이 기술이 이 문제의 포인트 중 하나였다.
i를 2씩 커지게 하여 한 쌍씩 가져와 out-in 을 할 수 있었다.


다음 날 다시 풀어보았다.
풀고나서 이전 풀이를 봤는데
for i in range(0,~~,2) 로 두 개씩 반복하는 기법을 쓰지 않고 풀었다.

IN에 모든 IN을 더하고 OUT에 모든 OUT을 다 더한뒤
OUT - IN 을 하여 총 시간을 구했다.

from collections import defaultdict 
import math

# 문자열 hhmm =  "03:30" -> 정수형 분 단위로 바꾸기 210
def time_to_minute(hhmm):
    hh, mm = hhmm.split(":")
    minute = int(hh) * 60 + int(mm)
    return minute

# fees = [기본시간,기본요금,단위시간,단위시간당 요금] [180, 5000, 10, 600]
# records = ["05:34 5961 IN", "06:00 0000 IN", "06:34 0000 OUT", "07:59 5961 OUT", "07:59 0148 IN", "18:59 0000 IN", "19:09 0148 OUT", "22:59 5961 IN", "23:00 5961 OUT"]

def solution(fees,records):
    
    # 내가 원하는 것
    # 오름차순으로 정렬된 차량번호 리스트
    # [ [ ] , [ ] , [ ] ] 이런식

    records_dict = defaultdict(list)

    for record in records: # record = "05:34 5972 IN"
        time, number, INorOUT = record.split(" ")

        records_dict[number].append([time,INorOUT])

    sorted_car_records = []
    for r in sorted(records_dict):
        sorted_car_records.append(records_dict[r])
      
    # sorted_car_records = [[['06:00', 'IN'], ['06:34', 'OUT'], ['18:59', 'IN']], [['07:59', 'IN'], ['19:09', 'OUT']], [['05:34', 'IN'], ['07:59', 'OUT'], ['22:59', 'IN'], ['23:00', 'OUT']]]
    # 0000, 0148, 5961 순의 record들이 들어감
    
    # IN,OUT이 홀수면 23:59 OUT 추가 해주기
    for i in range(len(sorted_car_records)):
        if len(sorted_car_records[i]) % 2 == 1:
            sorted_car_records[i].append(["23:59", "OUT"])

    
    answer = []

    for sorted_car_record in sorted_car_records:
        IN = 0
        OUT = 0
        for hhmm, INorOUT in sorted_car_record:
            hhmm = time_to_minute(hhmm)
            if INorOUT == "IN":
                IN += hhmm
            else:
                OUT += hhmm

        total = OUT - IN
        fee = 0

        # fees = [기본시간,기본요금,단위시간,단위시간당 요금] [180, 5000, 10, 600]
        if total <= fees[0]: # total이 기본시간보다 안나왔을 때,
            fee = fees[1] # 요금은 기본요금
        
        else:
            fee = fees[1] + math.ceil((total -  fees[0]) / fees[2]) * fees[3]
        
        answer.append(fee)

    return answer
profile
Frontend Engineers

0개의 댓글