리스트

변수는 한 가지를 담습니다. 리스트는 많은 것을 순서대로 담으며, 모두 하나의 이름으로 관리합니다. 순위 리스트는 점수가 순서대로 나열된 것입니다. 퀴즈는 문제들의 모음입니다. 관련된 값들의 그룹을 관리해야 할 때, 리스트가 필요합니다.
리스트 생성하기
대괄호, 쉼표로 구분된 값들. 리스트는 어떤 유형이든 섞어서 담을 수 있으며, 빈 리스트도 시간이 지나면서 만들어 나갈 수 있는 시작점으로 유효하고 일반적입니다.
scores = [87, 92, 74, 65, 91]
players = ["민준", "지은", "준호"]
mixed = ["민준", 87, True, 3.14] # any types, though uncommon
empty = [][]는 채워나갈 계획이 있을 때 좋은 시작점입니다. 제 리스트의 대부분은 그렇게 시작해요, 비어있고 채워질 때를 기다리며. 인덱싱과 슬라이싱
리스트는 문자열과 같은 번호 체계를 사용합니다: 위치는 0부터 시작하고, 음수는 끝에서부터 센다. 위치로 모든 항목을 읽을 수 있습니다. 리스트는 가변이므로, 특정 위치에 쓸 수도 있습니다.
scores = [87, 92, 74, 65, 91]
scores[0] # 87 (first)
scores[-1] # 91 (last)
scores[1:3] # [92, 74]
scores[:2] # [87, 92]
scores[::-1] # [91, 65, 74, 92, 87] (reversed)
scores[0] = 90 # mutable: works (strings would raise TypeError)0부터 시작하고, 음수는 끝에서부터 센다, 그래서 scores[-1]은 마지막 것입니다. scores[1:3] 같은 슬라이스는 위치 1과 2를 가진 새로운 리스트를 줍니다. 제가 깨닫는 데 잠깐 걸렸던 부분: 리스트로는 위치에도 쓸 수 있습니다, scores[0] = 90, 문자열은 거부할 것입니다. 항목 추가하기
항목을 추가하는 세 가지 방법이 있습니다. append()는 끝에 단일 항목을 추가하며 거의 매번 사용하게 될 것입니다. insert()는 특정 위치에 추가합니다. extend()는 다른 리스트를 병합합니다.
scores = [87, 92, 74]
scores.append(65) # [87, 92, 74, 65]
scores.insert(1, 100) # [87, 100, 92, 74, 65]
scores.extend([55, 71]) # [87, 100, 92, 74, 65, 55, 71]흔한 실수: 리스트를 가진 append()는 전체 리스트를 하나의 항목으로 추가하여, 리스트 안의 리스트를 줍니다. 대신 병합하려면 extend()를 사용하세요:
scores.append([55, 71]) # [..., [55, 71]] nested list, probably wrong
scores.extend([55, 71]) # [..., 55, 71] merged, correctappend()는 끝에 하나의 항목을 붙이며 거의 매번 도달하게 될 것입니다. insert()는 위치에 항목을 놓고, extend()는 다른 리스트를 병합합니다. 클래식한 실수: 리스트를 append()하면 리스트 안에 리스트를 얻으므로, 병합하려 할 때는 extend()를 사용하세요. 항목 제거하기
항목을 제거하는 네 가지 도구가 있습니다. remove()는 값으로 검색합니다. pop()은 위치로 제거하고 항목을 반환합니다. del은 위치로 제거하며 반환 값이 없습니다. clear()는 전체 리스트를 비웁니다.
scores = [87, 92, 74, 65, 91]
scores.remove(74) # removes first occurrence of 74
scores.pop() # removes and returns last item (91)
scores.pop(0) # removes and returns item at position 0 (87)
del scores[1] # removes at position 1, no return value
scores.clear() # removes everything리스트에 값이 없으면 remove()는 ValueError를 발생시킵니다. 확실하지 않으면 먼저 in으로 확인하세요:
if 74 in scores:
scores.remove(74)remove()는 값으로 삭제하며 첫 번째 일치만, 값이 없으면 ValueError를 발생시키므로, 확실하지 않을 때는 먼저 in으로 확인하세요. pop()은 위치로 제거하고 항목을 반환하며, del은 위치로 제거하고 아무것도 반환하지 않습니다. 정렬
sorted()는 새로운 정렬된 리스트를 반환하고 원본을 건드리지 않습니다. .sort()는 제자리에 리스트를 정렬하고 None을 반환합니다. 이 차이가 들리는 것보다 더 중요합니다.
scores = [87, 42, 96, 55, 71]
ranked = sorted(scores) # [42, 55, 71, 87, 96] (new list)
scores.sort() # sorts in place, returns None
scores.sort(reverse=True) # [96, 87, 71, 55, 42]
result = scores.sort() # result is None, not the sorted listsorted()는 새로운 정렬된 리스트를 주며 원본은 그대로 둡니다. .sort()는 리스트를 재배열하고 `None`을 반환하므로, x = scores.sort()는 리스트가 아닌 None을 줍니다. 저는 그 정확한 실수를 한 번 이상 했어요. 유용한 연산
파이썬은 리스트에 직접 작동하는 내장 도구 세트를 가지고 있습니다. len(), sum(), min(), max()는 항상 도달할 네 가지입니다.
scores = [87, 92, 74, 65, 91]
len(scores) # 5
sum(scores) # 409
min(scores) # 65
max(scores) # 92
scores.count(87) # 1
scores.index(74) # 2
74 in scores # True
74 not in scores # False
scores.copy() # shallow copy
scores.reverse() # reverses in placelen(), sum(), min(), max()는 모두 리스트에 직접 작동하며, 설정이 필요 없습니다. in은 뭔가 있는지 묻고, .count()는 몇 번 나타나는지 세며, .index()는 첫 번째 일치의 위치를 찾습니다. 반복 처리
for 루프는 리스트를 한 번에 하나의 항목으로 순회합니다. for 뒤의 변수는 순서대로 각 항목을 받습니다. 위치도 필요할 때, enumerate()는 수동 카운터 없이 둘 다를 줍니다.
players = ["민준", "지은", "준호"]
for player in players:
print(player)
for i, player in enumerate(players, start=1):
print(f"{i}. {player}")
# 1. 민준
# 2. 지은
# 3. 준호for과 enumerate()는 제어 흐름 장에서 전체 처리됩니다. 짧은 버전: for player in players는 항목당 한 번 실행되고, enumerate()는 모든 반복에서 위치와 값을 줍니다.
중첩된 리스트
리스트는 다른 리스트를 포함할 수 있습니다. 이것이 그리드나 테이블을 표현하는 방법입니다: 행들의 리스트, 각 행이 값들의 리스트입니다. 두 세트의 대괄호는 항목에 접근합니다: 첫 번째는 행을 선택하고, 두 번째는 열을 선택합니다.
grid = [
[1, 2, 3],
[4, 5, 6],
[7, 8, 9],
]
grid[0] # [1, 2, 3]
grid[1][2] # 6 (row 1, column 2)grid[1][2], 첫 번째는 행을 선택하고, 두 번째는 선택합니다. 가변성: 함정
이것은 거의 모두를 놀라게 합니다. 리스트를 새로운 변수에 할당하는 것은 복사본을 만들지 않습니다. 두 이름은 같은 리스트를 가리킵니다. 하나를 변경하면 다른 하나도 변경합니다. 독립적인 복사본을 얻으려면 명시적으로 요청해야 합니다.
a = [1, 2, 3]
b = a # b is not a copy; it points at the same list
b.append(4)
print(a) # [1, 2, 3, 4] (changed: a and b are the same list)b = a.copy() # independent copy
b = list(a) # same result
b = a[:] # also the same
# Nested lists still share their inner objects:
matrix = [[1, 2], [3, 4]]
copy = matrix.copy()
copy[0].append(99)
print(matrix) # [[1, 2, 99], [3, 4]] (inner list was shared)b = a는 복사본을 만들지 않습니다, 두 이름은 같은 리스트를 가리키므로, 하나를 통한 변경이 다른 하나에 표시됩니다. 독립적인 리스트의 경우 물어봐야 합니다: .copy(), list(a), 또는 a[:]. 이것은 처음에는 거의 모두를 놀라게 합니다, 저도 포함. 더 많은 메서드
| 메서드 | 하는 일 |
|---|---|
.append(item) | 끝에 추가 |
.insert(i, item) | 위치 i에 삽입 |
.extend(iterable) | 이터러블의 모든 항목 추가 |
.remove(value) | 값의 첫 번째 발생 제거 |
.pop(i) | 위치 i의 항목 제거 및 반환 (기본: 마지막) |
.clear() | 모든 항목 제거 |
.index(value) | 첫 번째 발생의 위치 |
.count(value) | 발생 수 |
.sort() | 제자리에 정렬 |
.reverse() | 제자리에 역순 |
.copy() | 얕은 복사 반환 |
실제로
점수 추적 만들기: 결과를 추가하고, 정렬하고, 요약을 출력하세요.
scores = []
scores.append(87)
scores.append(54)
scores.append(92)
scores.append(67)
scores.append(45)
scores.sort(reverse=True)
print(f"Ranked scores: {scores}")
print(f"Highest: {scores[0]}")
print(f"Lowest: {scores[-1]}")
print(f"Average: {sum(scores) / len(scores):.1f}")
print(f"Top 3: {scores[:3]}")
