Algorithm

백준 문제 풀이 (2231, 2609, 2846, 2953)

김디니 2022. 7. 26. 17:12

2609

최대공약수와 최소공배수

#유클리드 호제
A, B = map(int, input().split()) # 두 입력값을 받는다. (24, 18)
a, b = A, B			# 받은 입력값을 c, d에 넣어준다. 

while b != 0:		# b가 0이 아닐동안(?) 반복문을 실행한다. 즉, b가 0이 될 때 까지 반복문을 실행하고, 0이 되면 반복문을 종료한다. 
    a = a % b		# a와 b를 나눈 나머지 값을 a에 넣어준다. (a는 6이 된다)
    a, b = b, a		# a와 b의 값을 바꿔준다. 
    				# b가 0이 될 때 까지 반복한다. 

# gcd				# 최대공약수
print(a)			# b가 0이 될 시점의 a를 출력한다. (6)

#lcm				# 최소공배수
print(A*B//a)		# 두 입력값에 최대공약수를 나눈 몫을 출력한다. (72)

A와 B의 최대공약수는 B와 A%B의 최대공약수와 같다. 

입력값을 대문자 A, B에 받고, 소문자 a, b에 옮긴다. 이는 입력값 그대로의 A, B를 추후 최소공배수에 이용하기 위함이다. 

 

while문을 통해 b가 0이 아닐동안 즉, b가 0이 될 때 까지

a, b 를 나눈 나머지 값을 a에 옮기고, a와 b의 값을 서로 바꾼다. 

이 과정을 계속 반복하다 보면 a가 먼저 0이 된다. 

즉, 나머지 값이 0이 될 때 b의 값이 최대공약수가 된다. (이후 a와 b의 값을 서로 바꾸기 때문에 a값을 출력한다)

 

 

2846

오르막길

# 오르막길

n = int(input())                       # 입력값은 5로 가정
nums = list(map(int, input().split())) # 입력값을 리스트 형태로 담아준다. 
cnt = 0                                # 빼준 값을 저장(임시)
result = []                            # 최종 오르막길 값을 저장

for i in range(n - 1):                 # if 문에 [i+1]로 다음 값과 비교하기 때문에 n에서 1을 빼줘야 한다. 
                                       # n을 넣는다면 [i+1]에서 범위에 있는 값이 없기 때문에 오류가 난다. 

    if nums[i + 1] > nums[i]:          # 만약 다음 인덱스 값이 크다면
        cnt += (nums[i + 1] - nums[i]) # 빼줘서 cnt에 값을 넣는다. 

    else:         		       # 만약 다음 인덱스가 같거나 작다면 (오르막길이 아닐 경우)
        result.append(cnt)             # 위 cnt값(인덱스를 빼준 값)을 result에 넣어주고 
        cnt = 0                        # cnt는 0으로 초기화한다. 
                                       # 두 번째 if문에서 cnt(빼준)값을 result에 넣는 이유는 더 큰 오르막길이 있을 경우를 위함

result.append(cnt)                     # for문을 반복하여 오르막길 값을 구한뒤 for문이 종료되고 마지막으로 계산한 값을 result에 넣어준다. 

print(max(result))                     # result에 저장된 큰 수를 출력한다. 

# 숫자가 커질 때 더하고 작아질 때 0으로 초기화한다.

n은 5, nums는 1 2 1 4 5 라고 가정해보자. 

cnt는 인덱스의 값끼리 빼준 결과값을 임시적으로 저장해줄 변수이고, 

result는 최종적으로 오르막길의 크기를 저장할 변수이다. 

 

for문의 range에 n-1을 함께 명시해준다. (n -1은 4이기 때문에 인덱스는 0, 1, 2, 3가 된다.)

이는 if문의 '다음 인덱스' 의 [i + 1]을 위함이다. 

만약 range(n)으로 명시한다면 , if문에서 인덱스의 끝 위치인 3보다 더 큰 인덱스 값(4)이 없기 때문에 에러가 난다. 

 

if문을 통해 오르막길임을 확인해준다.

현재 인덱스 위치가 0(i)일 때, 다음 인덱스 위치(1)값은 2이고 현재 인덱스 값은 1이다. 

2 -1 은 1이기 때문에 cnt에 값을 넣어준다. 

 

다음 인덱스의 값은 1이고 오르막길이 아니기 때문에 cnt에 있었던 값인 1을 result에 넣어주고, cnt는 0으로 초기화한다. 

(다음 오르막길의 크기를 계산하기 위해)

 

 

2953

나는요리사다

# 나는 요리사다
order = 0 # 순서 저장
result = 0  # 최종 점수 저장

for i in range(5): # 5번 입력값을 반복하며 받는다.
    score = list(map(int, input().split())) # 나열하여 입력하는 입력값을 리스트에 담아준다.
                                            # result에 값을 저장하기 위해

    if sum(score) > result: # 현재 합계 점수가 이전의 합계 점수보다 크다면
        result = sum(score) # result에 새로운 값을 저장한다. 
        order = i + 1     # 입력한 순서를 나타내기 위해 i에 1을 더하여 현재 입력 순서를 나타낸다. 
        				  # i는 0부터 시작하므로 현재 순서 값을 저장하기 위해서는 +1 한다. 

print(order, result)

 

order는 순서를 저장하기 위해, result는 최종 점수를 저장하기 위해 변수를 만든다. 

 

나열된 입력값을 리스트로 저장해준다. (score)

 

if문을 통해 나열된 점수들을 합해주고,

이전의 합계 점수와 비교한다.

현재 계산된 합계 점수가 크다면 result에 저장하고, 현재 순서를 order에 저장한다. 

 

2231

분해합

N = int(input())                        # 입력받을 정수

for i in range(1, N + 1):               # 1부터 N까지 (문제 예 : 1부터 216 까지)
    num_list = list(map(int, str(i)))   # 분배합 리스트를 만들어준다 (정답 기준 [1, 9, 8])
    sum_ = i + sum(num_list)            # 순회하는 i (1 ~ 216)와 분배합 리스트를 더한 값(i를 쪼개서 더해줌)을 sum_에 저장한다
    if(sum_ == N):                      # 만약 (if) sum_ 값이 input 값과 같다면
        print(i)                        # i를 출력
        break                           # 끝 자리까지 순회를 돌 필요가 없기 때문에 break 이용해서 끊어준다!
    elif i >= N:
        print('0')                        # 결과를 출력

# 피드백) result에 할당하지 않고 i를 출력하는 방식으로 바꿨고, 생성자가 없을 때 0을 출력하는 elif 문을 추가했습니다!!