본문 바로가기

Python

3-6. 리스트/딕셔너리 내포 표현식

파이썬 리스트/딕셔너리 내표 포함식 타이틀이미지

 

안녕하세요! 지난 시간에는 파이썬의 주요 자료구조인 리스트, 튜플, 딕셔너리, 세트가 제공하는 다양한 메서드들을 총정리했습니다. 이제 여러분은 데이터를 효율적으로 저장하고 조작할 수 있는 여러 가지 방법을 익히셨을 거예요.

이번 시간에는 파이썬 코드를 더욱 간결하고 "파이썬스럽게(Pythonic)" 작성할 수 있게 해주는 특별한 문법인 **내포 표현식(Comprehension)**에 대해 알아보겠습니다. 주로 **리스트 내포(List Comprehension)**와 **딕셔너리 내포(Dictionary Comprehension)**를 통해 기존의 반복문보다 훨씬 짧고 직관적인 코드로 새로운 컬렉션을 생성할 수 있습니다.

내포 표현식은 처음에는 조금 낯설 수 있지만, 파이썬 개발에서 매우 중요하고 자주 사용되니 잘 익혀두시면 코딩 실력을 한 단계 업그레이드할 수 있을 것입니다.


Part 1: 리스트 내포(List Comprehension) - 간결하게 리스트 만들기

리스트 내포는 기존 리스트나 다른 반복 가능한 객체(iterable)를 기반으로 새로운 리스트를 생성하는 간결한 방법입니다. for 반복문과 if 조건문을 한 줄에 결합하여 사용할 수 있습니다.

1. 기본 형식: [표현식 for 항목 in 반복_가능한_객체]

  • 설명: 반복_가능한_객체에서 항목을 하나씩 꺼내어, 그 항목에 표현식을 적용한 결과를 모아 새로운 리스트를 만듭니다.

예시: 1부터 5까지의 숫자를 제곱한 리스트 만들기

Python
 
# 파일 이름: list_comprehension_basic.py

# 일반적인 for 문 사용
squares_normal = []
for num in range(1, 6): # 1, 2, 3, 4, 5
    squares_normal.append(num ** 2)
print(f"일반 for 문: {squares_normal}")

# 리스트 내포 사용
squares_comprehension = [num ** 2 for num in range(1, 6)]
print(f"리스트 내포: {squares_comprehension}")

# 문자열을 대문자로 변환한 리스트
words = ["apple", "banana", "cherry"]
upper_words = [word.upper() for word in words]
print(f"대문자 변환: {upper_words}")

 

[VS Code 터미널 출력]

파이썬 리스트 내포 기본 사용 예시

2. 조건 추가: [표현식 for 항목 in 반복_가능한_객체 if 조건]

  • 설명: 반복_가능한_객체에서 항목을 하나씩 꺼내고, 조건이 True인 항목에만 표현식을 적용한 결과를 모아 새로운 리스트를 만듭니다.

예시: 1부터 10까지의 숫자 중 짝수만 제곱한 리스트 만들기

Python
 
# 파일 이름: list_comprehension_if.py

# 일반적인 for 문과 if 문 사용
even_squares_normal = []
for num in range(1, 11):
    if num % 2 == 0: # 짝수만 선택
        even_squares_normal.append(num ** 2)
print(f"일반 for/if 문: {even_squares_normal}")

# 리스트 내포 사용
even_squares_comprehension = [num ** 2 for num in range(1, 11) if num % 2 == 0]
print(f"리스트 내포 (조건): {even_squares_comprehension}")

# 특정 길이 이상의 단어만 선택
long_words = ["apple", "banana", "cat", "dog", "elephant"]
filtered_words = [word for word in long_words if len(word) >= 5]
print(f"길이 필터링: {filtered_words}")

 

 

[VS Code 터미널 출력]

파이썬 리스트 내포에 조건 추가 예시

 

3. 중첩 for 문 사용: [표현식 for 항목1 in 반복1 for 항목2 in 반복2]

  • 설명: 여러 개의 for 루프를 중첩하여 리스트를 만들 수 있습니다. 바깥쪽 for 루프부터 순서대로 실행됩니다.

예시: 구구단 결과 리스트 만들기

Python
 
# 파일 이름: list_comprehension_nested.py

# 일반적인 중첩 for 문 사용
multiplication_table_normal = []
for i in range(2, 4): # 2단, 3단
    for j in range(1, 3): # x1, x2
        multiplication_table_normal.append(f"{i}x{j}={i*j}")
print(f"일반 중첩 for 문: {multiplication_table_normal}")

# 리스트 내포 사용
multiplication_table_comprehension = [f"{i}x{j}={i*j}" for i in range(2, 4) for j in range(1, 3)]
print(f"리스트 내포 (중첩): {multiplication_table_comprehension}")

# 중첩 리스트 평탄화 (flatten)
list_of_lists = [[1, 2], [3, 4], [5, 6]]
flattened_list = [num for sublist in list_of_lists for num in sublist]
print(f"평탄화된 리스트: {flattened_list}")

 
 

[VS Code 터미널 출력]

파이썬 리스트 내포에 중첩 for 문 사용 예시

Part 2: 딕셔너리 내포(Dictionary Comprehension) - 간결하게 딕셔너리 만들기

딕셔너리 내포는 리스트 내포와 유사하게, 반복 가능한 객체를 기반으로 새로운 딕셔너리를 생성하는 방법입니다. 키: 값 쌍을 한 줄에 정의합니다.

1. 기본 형식: {키_표현식: 값_표현식 for 항목 in 반복_가능한_객체}

  • 설명: 반복_가능한_객체에서 항목을 하나씩 꺼내어, 키_표현식과 값_표현식을 적용한 결과를 키: 값 쌍으로 모아 새로운 딕셔너리를 만듭니다.

예시: 숫자와 제곱 값을 키-값으로 가지는 딕셔너리 만들기

Python
 
# 파일 이름: dict_comprehension_basic.py

# 일반적인 for 문 사용
squares_dict_normal = {}
for num in range(1, 6):
    squares_dict_normal[num] = num ** 2
print(f"일반 for 문: {squares_dict_normal}")

# 딕셔너리 내포 사용
squares_dict_comprehension = {num: num ** 2 for num in range(1, 6)}
print(f"딕셔너리 내포: {squares_dict_comprehension}")

# 리스트에서 키와 값 생성
fruits = ["apple", "banana", "cherry"]
fruit_lengths = {fruit: len(fruit) for fruit in fruits}
print(f"과일 길이 딕셔너리: {fruit_lengths}")

 

 

[VS Code 터미널 출력]

파이썬 딕셔너리 내포 기본 사용 예시

 

2. 조건 추가: {키_표현식: 값_표현식 for 항목 in 반복_가능한_객체 if 조건}

  • 설명: 반복_가능한_객체에서 항목을 하나씩 꺼내고, 조건이 True인 항목에 대해서만 키: 값 쌍을 생성합니다.

예시: 특정 점수 이상의 학생만 딕셔너리에 추가하기

Python
 
# 파일 이름: dict_comprehension_if.py

student_scores = {"Alice": 85, "Bob": 92, "Charlie": 78, "David": 60}

# 80점 이상인 학생만 필터링 (일반 for 문)
passed_students_normal = {}
for name, score in student_scores.items():
    if score >= 80:
        passed_students_normal[name] = score
print(f"일반 for/if 문: {passed_students_normal}")

# 딕셔너리 내포 사용
passed_students_comprehension = {name: score for name, score in student_scores.items() if score >= 80}
print(f"딕셔너리 내포 (조건): {passed_students_comprehension}")

 

[VS Code 터미널 출력]

파이썬 딕셔너리 내포에 조건 추가 예시

3. 키와 값 바꾸기 (Swap Key and Value)

  • 딕셔너리 내포를 활용하여 딕셔너리의 키와 값을 서로 바꿀 수도 있습니다. (단, 값이 고유해야 합니다. 값이 중복되면 키가 중복되어 마지막 값만 남게 됩니다.)

예시:

Python
 
# 파일 이름: dict_comprehension_swap.py

original_dict = {"A": 1, "B": 2, "C": 3}
# 키와 값을 바꿔 새로운 딕셔너리 생성
swapped_dict = {value: key for key, value in original_dict.items()}
print(f"원본 딕셔너리: {original_dict}")
print(f"키-값 바꾼 딕셔너리: {swapped_dict}")

# 값이 중복된 경우 (주의! 'd': 2는 덮어씌워짐)
duplicate_value_dict = {"a": 1, "b": 2, "c": 3, "d": 2}
swapped_with_duplicate = {value: key for key, value in duplicate_value_dict.items()}
print(f"\n원본 (값 중복): {duplicate_value_dict}")
print(f"키-값 바꾼 딕셔너리 (값 중복): {swapped_with_duplicate}")

 

[VS Code 터미널 출력]

파이썬 딕셔너리 내포로 키와 값 바꾸기 예시

Part 3: 내포 표현식의 장점과 사용 시기

내포 표현식은 다음과 같은 장점 덕분에 파이썬에서 매우 선호됩니다.

  • 코드 간결성: 여러 줄의 for 루프와 append()/딕셔너리 할당 코드를 한 줄로 줄일 수 있습니다.
  • 가독성: 익숙해지면 코드가 어떤 작업을 하는지 한눈에 파악하기 더 쉽습니다.
  • 성능: C로 구현된 내부 함수를 사용하기 때문에 일반적인 for 루프보다 대체로 더 빠르게 동작합니다.

언제 사용하는 것이 좋을까?

  • 새로운 리스트나 딕셔너리 생성: 기존 데이터를 기반으로 새로운 컬렉션을 만들 때 가장 적합합니다.
  • 필터링: 특정 조건에 맞는 요소만 포함하는 새로운 컬렉션을 만들 때.
  • 변환: 각 요소를 다른 형태로 변환하여 새로운 컬렉션을 만들 때.

주의할 점:

  • 복잡성: 너무 복잡한 로직을 내포 표현식 하나에 다 담으려 하면 오히려 가독성이 떨어질 수 있습니다. 2단계 이상의 중첩이나 너무 긴 조건문이 필요하다면, 일반 for 루프나 함수로 분리하여 작성하는 것이 더 좋습니다.
  • 디버깅: 한 줄로 되어 있어 디버깅이 어려울 수 있습니다.

마무리하며

이번 시간에는 파이썬의 강력하고 간결한 문법인 **리스트 내포(List Comprehension)**와 **딕셔너리 내포(Dictionary Comprehension)**에 대해 자세히 알아보았습니다. 이 표현식들은 반복문을 사용하여 새로운 컬렉션을 생성할 때 코드의 양을 줄이고 가독성을 높이며 성능까지 향상시키는 매우 효과적인 방법입니다.

처음에는 익숙해지는 데 시간이 걸릴 수 있지만, 꾸준히 연습하여 여러분의 파이썬 코드를 더욱 효율적이고 멋지게 만들어 보세요!

이로써 파이썬의 기본적인 자료구조에 대한 포스팅이 마무리됩니다. 다음 챕터부터는 프로그램의 기능을 재사용 가능한 단위로 묶는 **함수(Function)**에 대해 자세히 알아보겠습니다.


궁금한 점이 있다면 언제든지 질문해주세요! 다음 포스팅에서 만나요!

반응형