Study/Python

[Python] 반복문

the.Dev.Cat 2026. 3. 7. 23:24

 

동빈나 채널의 파이썬 문법 부수기 유튜브 강의를 참고하여 정리한 내용이다.

 

파이썬의 for문은 C의 for문과 구조가 다르고, enumerate, zip 같은 유용한 도구들도 있다.

중첩 반복문에서 탈출하는 방법도 파이썬만의 패턴이 있다.

 


 

while문

기본 구조

while 조건:
    실행할 코드

조건이 True인 동안 계속 반복한다.

 

1부터 9까지의 합

i = 1
result = 0

while i <= 9:
    result += i
    i += 1

print(result)  # 45

 

홀수만 합산

i = 1
result = 0

while i <= 9:
    if i % 2 == 1:  # 홀수인 경우
        result += i
    i += 1

print(result)  # 25 (1+3+5+7+9)

 

무한 루프 주의

i = 1
while i <= 10:
    print(i)
    # i += 1을 빠뜨리면 무한 루프

 

while문에서 루프 변수를 빠뜨리거나 잘못 갱신하면 무한 루프가 된다. 코딩테스트에서 시간 초과 원인 중 하나다.

의도적인 무한 루프는 while True:로 쓰고, break로 탈출한다.

while True:
    cmd = input()
    if cmd == "exit":
        break
    print(f"입력: {cmd}")

 


 

for문

기본 구조

for 변수 in 이터러블:
    실행할 코드

 

파이썬의 for는 이터러블(리스트, 문자열, range 등)의 원소를 하나씩 꺼내는 구조다.

fruits = ["apple", "banana", "cherry"]

for fruit in fruits:
    print(fruit)
# apple
# banana
# cherry

# 문자열도 순회 가능
for char in "hello":
    print(char)
# h, e, l, l, o 순서로

 


 

range()

숫자 범위를 생성한다. for문에서 가장 많이 쓰인다.

# range(stop)        - 0부터 stop-1까지
# range(start, stop) - start부터 stop-1까지
# range(start, stop, step) - start부터 stop-1까지 step 간격으로

for i in range(5):
    print(i, end=" ")  # 0 1 2 3 4

for i in range(1, 6):
    print(i, end=" ")  # 1 2 3 4 5

for i in range(0, 10, 2):
    print(i, end=" ")  # 0 2 4 6 8

 

1부터 30까지의 합

result = 0
for i in range(1, 31):
    result += i
print(result)  # 465

 

음수 step - 역순 순회

for i in range(5, 0, -1):
    print(i, end=" ")  # 5 4 3 2 1

# 리스트 역순 순회
nums = [1, 2, 3, 4, 5]
for i in range(len(nums) - 1, -1, -1):
    print(nums[i], end=" ")  # 5 4 3 2 1

# reversed() 가 더 간결
for n in reversed(nums):
    print(n, end=" ")  # 5 4 3 2 1

 


 

continue와 break

continue - 현재 반복 건너뛰기

for i in range(1, 11):
    if i % 2 == 0:
        continue  # 짝수면 건너뜀
    print(i, end=" ")  # 1 3 5 7 9

 

break - 반복 완전 종료

for i in range(1, 11):
    if i == 5:
        break  # 5에서 멈춤
    print(i, end=" ")  # 1 2 3 4

 


 

종합 예제 : 합격 판단

점수가 80점 이상이면 합격, 부정행위 학생은 결과와 무관하게 탈락시키는 예제다.

scores = [85, 72, 90, 63, 88, 76]
cheaters = {2, 4}  # 인덱스 2, 4번이 부정행위

for i in range(len(scores)):
    if i in cheaters:
        print(f"{i}번: 부정행위 탈락")
        continue
    if scores[i] >= 80:
        print(f"{i}번: 합격 ({scores[i]}점)")
    else:
        print(f"{i}번: 불합격 ({scores[i]}점)")

# 0번: 합격 (85점)
# 1번: 불합격 (72점)
# 2번: 부정행위 탈락
# 3번: 불합격 (63점)
# 4번: 부정행위 탈락
# 5번: 불합격 (76점)

 


 

중첩 반복문 : 구구단

for i in range(2, 10):
    for j in range(1, 10):
        print(f"{i} x {j} = {i * j}")
    print()  # 단 사이 빈 줄

 


 

enumerate()

인덱스와 값을 동시에 꺼낼 때 쓴다. 인덱스 변수를 별도로 관리할 필요가 없다.

fruits = ["apple", "banana", "cherry"]

# 인덱스 없이 순회
for fruit in fruits:
    print(fruit)

# 인덱스 필요할 때 - range(len()) 방식
for i in range(len(fruits)):
    print(i, fruits[i])

# enumerate() - 더 깔끔
for i, fruit in enumerate(fruits):
    print(i, fruit)
# 0 apple
# 1 banana
# 2 cherry

# 시작 인덱스 지정
for i, fruit in enumerate(fruits, start=1):
    print(i, fruit)
# 1 apple
# 2 banana
# 3 cherry
# 실전: 최댓값의 인덱스 찾기
nums = [3, 7, 1, 9, 4]
max_idx = 0
for i, n in enumerate(nums):
    if n > nums[max_idx]:
        max_idx = i
print(max_idx)  # 3

 


 

zip()

여러 이터러블을 병렬로 순회한다.

names = ["Alice", "Bob", "Charlie"]
scores = [85, 92, 78]

for name, score in zip(names, scores):
    print(f"{name}: {score}점")
# Alice: 85점
# Bob: 92점
# Charlie: 78점

 

길이가 다른 경우 짧은 쪽에 맞춰 끊긴다.

a = [1, 2, 3, 4, 5]
b = [10, 20, 30]

for x, y in zip(a, b):
    print(x, y)
# 1 10
# 2 20
# 3 30
# (a의 4, 5는 무시됨)
# 두 리스트의 원소별 합산
a = [1, 2, 3]
b = [4, 5, 6]
result = [x + y for x, y in zip(a, b)]
print(result)  # [5, 7, 9]

 


 

for-else / while-else

파이썬에만 있는 문법이다. break 없이 반복이 정상적으로 끝났을 때 else 블록이 실행된다.

# 소수 판별
n = 17

for i in range(2, n):
    if n % i == 0:
        print(f"{n}은 소수가 아님")
        break
else:
    # break 없이 for가 끝났다 = 약수를 못 찾았다 = 소수
    print(f"{n}은 소수")
# 17은 소수
# while-else도 같은 방식
i = 0
while i < 5:
    if i == 3:
        break
    i += 1
else:
    print("while 정상 종료")  # break로 끝나면 실행 안 됨

 

break 여부를 별도 플래그로 체크하는 코드를 for-else로 깔끔하게 대체할 수 있다.

 


 

중첩 반복문 탈출 패턴

중첩 반복문에서 break는 가장 안쪽 루프만 빠져나온다.

# break는 안쪽 for만 탈출
for i in range(3):
    for j in range(3):
        if j == 1:
            break
    print(i)  # 바깥 for는 계속 돔
# 0
# 1
# 2

 

플래그 변수 방법

found = False

for i in range(5):
    for j in range(5):
        if i + j == 6:
            found = True
            break
    if found:
        break

print(f"i={i}, j={j}")  # i=2, j=4 (또는 다른 조합)

 

함수 return 방법 (더 깔끔)

def find_pair(target):
    for i in range(5):
        for j in range(5):
            if i + j == target:
                return i, j
    return None

result = find_pair(6)
print(result)  # (2, 4)

 

함수로 분리하고 return으로 탈출하는 방식이 플래그보다 코드가 명확하다.

 


 

무한 루프 디버깅

코딩테스트에서 시간 초과가 나면 무한 루프를 의심한다.

# 자주 하는 실수 1: 루프 변수 갱신 빠뜨리기
i = 0
while i < 10:
    print(i)
    # i += 1  빠뜨리면 무한 루프

# 자주 하는 실수 2: 조건이 항상 True
while True:
    x = int(input())
    if x < 0:
        continue  # break가 아닌 continue - 루프를 절대 탈출 못 함

# 자주 하는 실수 3: 리스트를 순회하면서 수정
nums = [1, 2, 3, 4, 5]
for n in nums:
    if n % 2 == 0:
        nums.remove(n)  # 순회 중 수정 - 예상치 못한 동작
print(nums)  # [1, 3, 5]가 아닌 [1, 3, 5] 가 될 수도, 아닐 수도 있음

# 올바른 방법: 새 리스트로
nums = [n for n in nums if n % 2 != 0]

 


 

에러 상황

무한 루프 → 시간 초과

# 종료 조건이 없는 while
i = 10
while i > 0:
    print(i)
    i += 1  # i가 계속 커짐 - 절대 0 이하가 되지 않음

 

TypeError - 정수를 직접 순회

n = 5
for i in n:  # TypeError: 'int' object is not iterable
    print(i)

for i in range(n):  # 올바름
    print(i)

 

IndexError - 범위 초과

nums = [1, 2, 3]
for i in range(len(nums) + 1):  # range(4) - 인덱스 3은 없음
    print(nums[i])  # IndexError: list index out of range