공부/글또 9기

코테 초보 탈출기 기록 2 - 파이썬 기초 문제 풀이

Moana96815 2024. 1. 7. 20:59

약 6주 동안 링크에 있는 '준비운동 PART1. 튼튼한 기본기'를 풀었습니다. 11문제 중 9문제를 풀고, 2문제는 풀지 못했습니다. 기초인데 완벽히 풀지 못해서 아쉽긴 하지만, 다음 기회에 좀 더 성장하길 바라며, 오답 기록을 남기려고 합니다. 문제와 저의 풀이 혹은 다른 사람의 풀이를 첨부하고, 해당 문제에 대한 저의 생각을(제가 생각하는 이 문제의 핵심, 풀면서 어려웠던 점, 추후에 보완할 점 등) 남길 예정입니다.

 


 

입력값 할당하는 법

오답을 정리하기 전에 알고리즘 문제를 풀기 전에 꼭 알아두어야 하는 여러 가지 형태의 입력값 받는 방법을 간단히 정리하려고 합니다. 알고리즘 문제를 오랫동안 풀지 않으면, 까먹어서 매번 구글링을 하는데, 이 글에 남겨둔다면, 더 이상 문제 풀 때 로딩이 덜 걸릴 것 같습니다.

 

 

숫자나 문자 입력값을 a에 할당하는 방법 

a = input()

 

 

같은 줄에 공백이 있는 2개의 숫자 타입 입력값을 a,b에 할당하는 방법 

a,b = map(int,input().split())

 

 

같은 줄에 공백이 있는 숫자 타입 입력값을 리스트 N에 할당하는 방법 

N = list(map(int,input().split()))

 

 

9줄로 이루어진 숫자 타입 입력값을 리스트 N에 할당하는 방법 

N = list(int(input()) for _ in range(9))

 

 

여러 줄로 이루어진 배열을 arr에 할당하는 방법(단 n이 항상 정해져 있어야 함) 

arr = [list(map(int,input().split())) for _ in range(n)]

 


 

준비운동 PART 1. 튼튼한 기본기

 

📖2501번. 약수 구하기 (해결 O)

 

💯내 풀이

# p, q에 입력값 받기
p,q = map(int,input().split())

# a에 약수가 되는 값 넣기
a = []
for i in range(1,p+1):
    if p % i == 0:
        a.append(i)
        
# q번째 약수 값 출력        
if q <= len(a):
    print(a[q-1])
else :
    print(0)

 

해당 문제는 문제에 나와 있는 그대로 1부터 주어진 숫자까지 나머지가 0인 값인 약수를 찾은 후, n번째로 작은 수를 출력했습니다. 문제를 잘 해결했지만, 추후에는 좀 더 보기 좋게 숏코딩을 해보는 것도 좋을 것 같습니다.

 


 

📖3460번. 이진수 (해결 X)

 

💯내 풀이

# T에 테스트 갯수, n에 이진수로 변화할 값 할당
T = input()
n = int(input())

# 이진수로 변환할 값을 리스트 a에 할당
a = []
while True:
    if n != 1:
        a.append(n % 2)
        n = n // 2
    else:
        a.append(1)
        break

# 이진수로 변환한 값을 할당한 리스트 a에서 1의 위치 출력
for i in range(0,len(a)):
    if a[i] == 1:
        print(i,end=' ')

 

👀다른 사람 풀이

T = int(input())
 
for _ in range(T):
    n = bin(int(input()))[2:]
    for i in range(len(n)):
        if n[-i - 1] == '1':
            print(i, end=' ')

 

해당 문제는 이진수를 변환하는 것이 핵심이었는데, 저는 내장 함수가 있다는 것을 몰라서 2로 나누어 나머지를 할당하는 방식으로 접근했습니다. 문제에 제시된 예제 입력값을 출력하는 데는 문제가 없었지만, 테스트 개수가 2개 이상일 때, 값이 도출되지 않는다는 점을 놓쳤습니다. for 문을 이용하여 테스트 개수를 늘리면 될 것 같지만, 결국 스스로 해결은 하지 못해서 다른 사람들의 풀이를 참고해야 했습니다. 다른 사람의 풀이를 보니, bin 함수를 활용해서, 좀 더 쉽고 간결하게 풀 수 있다는 것을 알 수 있었습니다.

 


 

📖 10818번. 최소, 최대 (해결 O)

 

💯내 풀이

k = int(input())
N = list(map(int,input().split()))
print(min(N),max(N))

 

파이썬의 내장 함수 min, max를 활용하여, 나름대로 숏코딩을 했습니다. 언젠가 알고리즘을 대강 1회독 했던 기억을 떠올려보면, 추후에 두 수 비교하여 값 찾는 방법을 내장 함수를 활용하지 않고도 풀 수 있어야 했던 것 같습니다. 그런 비슷한 문제를 풀 때 해당 문제를 내장함수를 활용하지 않고 다시 풀어보면 좋을 것 같다는 생각이 들었습니다.

 


 

📖2460번. 지능형 기차2 (해결 O)

 

💯내 풀이

# arr에 입력값 할당
arr = [list(map(int,input().split())) for _ in range(10)]

# n에 처음 승객수 할당
n = arr[0][1]
# 행별로 최종 승객수 할당할 리스트
k = []

# 행에 첫번째 값은 빼주고, 두번째 값은 더해서 현재 승객수를 리스트 k에 값 추가
# 리스트 k에서 가장 큰 수 출력
for i,j in arr[1:]:
    n -= i
    n += j
    k.append(n)
print(max(k))

 

 

배열을 입력값으로 받는 것을 제외하면, 문제 풀이 자체는 접근하기 쉬운 문제였습니다. 배열을 할당하는 것은 이 글 상단에 정리해 뒀으므로 여기서는 생략합니다.

 


 

📖 10870번. 피보나치 수 5 (해결 O)

 

💯내 풀이

arr = [0,1]
n = int(input())
while (len(arr)) <= n:
    arr.append(arr[-1]+arr[-2])
print(arr[n])

 

피보나치 수를 구하는 데는 다양한 방법이(재귀함수, 제너레이터 활용 등) 있다는 것을 전에 봤던 기억이 있습니다. 그런데 막상 문제를 마주칠 때마다, 이론은 대충 아는데 활용을 하지 못해서인지 아직은 마지막 두 값을 더해서 구하는 방식으로 풀어보았습니다. 추후에 본격적으로 알고리즘 이론을 공부하게 되면 자연스럽게 그 이론에 걸맞게 풀 수 있지 않을까 기대해 봅니다.

 


 

📖2309번. 일곱 난쟁이(해결 O)

 

💯내 풀이

from itertools import permutations
p1 = list(int(input()) for _ in range(9))
for i in permutations(p1,7):
    if (sum(i)) == 100:
        for _ in sorted(i):
            print(_)
        break

 

주어진 값 10개 중에 7개의 조합으로 100을 만들어야 하는데, permutations 함수를 활용하여 문제를 해결했습니다.

 


 

📖 2609번. 최대 공약수와 최소 공배수 (해결 O)

 

💯내 풀이

a, b = map(int,input().split())

# a의 약수, b의 약수를 각각 리스트 a1, b1에 할당
a1 = [i for i in range(1,a+1) if a % i == 0]
b1 = [i for i in range(1,b+1) if b % i == 0]

# a1과 b1 모두가 갖고 있는 수 중 가장 큰값(최대 공약수), 최대 공약수를 활용한 최대 공배수 출력
c1 = [i for i in a1 if i in b1]
print(max(c1), a//max(c1)*b//max(c1)*max(c1),sep = '\n')

 

최대 공배수를 더 쉽게 구하는 방법도 존재하는데, 지금 저의 실력에는 이 방법이 최선인 것 같습니다. 추후에 좀 더 괜찮은 방법을 제 것으로 만든다면, 그때 보완하면 좋을 것 같습니다.

 


 

📖 2693번. N번째 큰 수(해결 O)

 

💯내 풀이

n = int(input())
arr = [list(map(int,input().split())) for _ in range(n)]

for i in range(n):
    print(sorted(arr[i],reverse = True)[2])

 

해당 문제는 문제 자체가 어려운 것은 아니지만, 리스트에 행별 리스트를 할당해서 활용하는 부분이 좀 어려웠습니다. 이 부분도 전 구글링을 통해 풀었고, 글 상단에 리스트 안에 리스트 받는 법을 정리해뒀습니다.

 


 

📖 1978번. 소수 찾기 (해결 O)

 

💯내 풀이

k = int(input())
N = list(map(int,input().split()))

# N에 할당된 값이 1과 같거나 작으면 정답 증가하지 않는 조건 추가
answer = 0
for i in N:
    count = 0
    if i <= 1:
        continue
    else:
# N에 할당된 값 하나씩 1부터 1씩 증가하며 나머지가 0인 갯수가 두개 인 값 찾으면 정답이 1 증가
        for j in range(1,i+1):
            if i % j == 0:
                count += 1
    if count == 2:
        answer += 1
print(answer)

 

특별히 추가로 적을 생각이 떠오르지 않아서, 해당 문제는 생략합니다.

 


 

📖 1292번. 쉽게 푸는 문제(해결 O)

 

💯내 풀이

k = []
a,b = map(int, input().split())
p = 1
while len(k) <= b:
    k = k + [p]*p
    p += 1
print(sum(k[a-1:b]))

 

 

해당 문제는 리스트를 반복하여 더할 수 있고, 리스트끼리 더했을 때 어떤 결과가 나오는지 알아야 풀 수 있는 문제였습니다. 알고리즘은 잘 몰라도, 전에 공부했던 기억으로 쉽게 풀 수 있었습니다.

 


 

📖 2581번. 소수(해결 X)

 

💯내 풀이

a = int(input())
b = int(input())

# a, b 사이에 모든 값을 리스트 k에 할당
k = list(range(a,b+1))

# a, b 사이에 소수에 해당하는 값을 리스트 a_l에 추가
a_l = []
for n in k:    
    p = []
    i = 1
    while i <= n:
        if n % i == 0:
            p.append(i)
            i += 1
        else:
            i += 1
    if len(p) == 2:
        a_l.append(n)
        
#a_l에 값이 존재 하지 않으면 -1을 출력
#a_l에 값이 존재하면 다 더한 값과 가장 작은 값 출력
if len(a_l) == 0:
    print(-1)
else:
    print(sum(a_l),min(a_l),sep='\n')

 

접근하는 방식은 나쁘지 않은 것 같은데, 코드 자체가 난잡하기도 하고, 결국 시간 초과라는 에러가 났습니다. 4년 전에 한참 파이썬을 사용했을 때는 분명 해결했던 문제인데, 이번에는 해결하지 못했습니다. 4년 전 코드는 공약수 개수가 2개인 값만 리스트에 추가하여 소수를 좀 더 깔끔하게 구했는데, 이번에는 공약수를 리스트에 넣고 리스트 안에 갯수가 몇 개인지 세느라 코드가 쓸데없이 길었네요. 어떤 부분에서 시간 초과 에러가 났는지는 제 눈에 잘 보이지 않아서, 추후에 다시 풀어보기로 하고 넘어가야겠습니다.

 


 

이상으로 11문제에 대한 정리는 모두 마쳤습니다. 전에는 깔끔하게 풀던 문제를 지금은 못 풀었다던가, 그간 파이썬을 잘 사용하지 않아서 잊었던 함수들이 있다는 등으로 조금 아쉬웠습니다. 하지만, 다시 문제를 풀다 보면, 잊었던 지식도 새로운 지식도 차곡차곡 잘 정리하여 실력이 향상되길 기대하며 본글을 마칩니다. 새해 첫 글인 만큼 부디 이번에는 알고리즘을 정복할 수 있기를 기원해 봅니다! 2024년 모두 원하는 것 다 이루세요! 파이팅입니다!

반응형