Skip to content

리스트(List)

25명의 학생들의 시험 점수를 계산하는 프로그램을 작성한다고 해보자. 개인별 점수를 저장할 변수를 score1, score2, ..., score25까지 25개의 변수가 필요하다. 학생이 100명, 1000명 증가한다면 인원에 맞는 변수의 선언은 비효율적이다.

C언어나 Java와 같은 언어에서는 다음과 같이 배열을 사용한다.

c
// 자료형 변수명[크기];
int score[25];
java
// 자료형[] 변수명 = new 자료형[크기];
int[] score = new int[25];

C, C++, Java는 배열을 선언한 후 같은 자료형을 저장하여 사용하는 방식이다. 파이썬에서는 리스트(list)를 사용한다.

python
score = [90, 92, ..., 88, 74]

리스트는 자료형을 선언하지 않고 리스트 이름을 선언한 후에 대괄호([]) 사이에 값을 늘여놓고 사용하거나 list()를 사용한다. 다른 프로그래밍 언어와 다르게 리스트에는 여러 자료형을 저장할 수 있다.

python
a = [90, 92, 84, 88, 74]
b = list((90, 92, 84, 88, 74))
c = ["파이썬", 900, 30.5, "자바", 850, 78.75]
d = list(("파이썬", 900, 30.5, "자바", 850, 78.75))
e = list("프로그래밍")
print(a, b, c, d, e, sep="\n") # print할 내용마다 줄 바꿈
plaintext
[90, 92, 84, 88, 74]
[90, 92, 84, 88, 74]
['파이썬', 900, 30.5, '자바', 850, 78.75]
['파이썬', 900, 30.5, '자바', 850, 78.75]
['프', '로', '그', '래', '밍']

인덱싱(Indexing)

리스트의 값을 사용하기 위해서 인덱스를 이해해야 한다. C, C++, Java와 마찬가지로 처음 값의 인덱스는 0이다.

python
a = [90, 91, 92, 93, 94, 95, 96]
print(a[0])
plaintext
90
90919293949596
인덱스0123456
-7-6-5-4-3-2-1

파이썬에서 리스트에 접근하는 인덱스는 음수를 지정할 수 있다. 음수로 지정한 경우 마지막 요소부터 접근한다. a[-1]인 경우 마지막 값인 96을 가져온다.

슬라이싱(Slicing)

순회가능한 객체의 일부를 가져오는 방법을 슬라이싱이라고 한다. 슬라이싱은 인덱싱과 비슷하게 사용한다. a[시작:끝]의 형태로 사용하며, 시작 인덱스는 포함하고 끝 인덱스는 포함하지 않는다. 즉, a[0:3]a[0], a[1], a[2]를 가져온다.

리스트 a의 슬라이싱 결과는 다음과 같다.

슬라이싱결과설명
a[0:3][90, 91, 92]a[0]부터 a[2]까지 값
a[3:5][93, 94]a[3]부터 a[4]까지 값
a[0:][90, 91, 92, 93, 94, 95, 96]a[0]부터 마지막까지
a[3:][93, 94, 95, 96]a[3]부터 마지막까지
a[:][90, 91, 92, 93, 94, 95, 96]리스트 a 전체
a[1:5:2][91, 93]a[1]부터 a[4]까지 2씩 건너뜀
a[::2][90, 92, 94, 96]처음부터 마지막까지 2씩 건너뜀
a[1::2][91, 93, 95]a[1]부터 마지막까지 2씩 건너뜀
a[-4:-2][93, 94]a[-4]부터 a[-3]까지 값
a[-4:][93, 94, 95, 96]a[-4]부터 마지막까지
a[100]IndexError인덱스 범위를 벗어남
a[5:100][95, 96]a[5]부터 마지막까지(인덱스가 범위를 초과한 경우 마지막까지)

슬라이싱은 문자열에도 동일하게 적용된다.

python
ct = "프로그래밍"
print(ct[1], ct[-1])
plaintext
로 밍

리스트 요소 수정하기

리스트 prog에는 프로그래밍 언어 4가지를 저장하였다. 첫 번째 언어인 CC++로 수정하려면 prog에 해당 인덱스를 표시하고 값을 할당하여 수정한다.

python
prog = ["C", "Java", "Python", "Go"]
prog[0] = "C++"
print(prog)
plaintext
['C++', 'Java', 'Python', 'Go']

그러나 인덱스를 벗어나 prog[4] = "Ruby"를 실행할 경우 에러(IndexError)가 발생한다.

IndexError: list assignment index out of range

리스트 내 요소의 값을 수정하는 것은 다른 언어의 배열 값을 수정하는 방법과 같지만 다음 예제를 통해 리스트의 특징을 알아보자.


리스트 복사 1

python
prog = ["C", "Python", "Java"]
myprog = prog
print("prog:", prog)
print("myprog:", myprog)
prog[0] = "C++"
print("prog:", prog)
print("myprog:", myprog)
plaintext
prog: ['C', 'Python', 'Java']
myprog: ['C', 'Python', 'Java']
prog: ['C++', 'Python', 'Java']
myprog: ['C++', 'Python', 'Java']

리스트 복사 2

python
prog = ["C", "Python", "Java"]
myprog = prog[:]
print("prog:", prog)
print("myprog:", myprog)
prog[0] = "C++"
print("prog:", prog)
print("myprog:", myprog)
plaintext
prog: ['C', 'Python', 'Java']
myprog: ['C', 'Python', 'Java']
prog: ['C++', 'Python', 'Java']
myprog: ['C', 'Python', 'Java']

myprog=prog라고 하면 myprogprog를 복제했다고 생각했을 것이다. 하지만 prog[0] 값을 수정하고 progmyprog를 출력하면 내용이 모두 변경된 것을 확인할 수 있다.

메모리 상에 있는 리스트를 여러 변수가 함께 사용하기 때문에 이와 같은 현상이 발생한다. 이 같은 현상을 얕은 복사(shallow copy)라고 한다. 리스트 값 전체를 다른 리스트에 복사하려면 myprog = prog[:]를 사용하여 리스트 prog 안에 모든 값을 myprog에 저장하는 것이다. 실행 결과를 확인하면 리스트 progmyprog의 요소 값들이 서로 다르다는 것을 알 수 있다.

리스트 연산

리스트 자료형도 몇 가지 연산을 지원한다. 별도의 함수를 사용하지 않고 연산자를 통한 예제를 통해 리스트 연산을 알아보자.

python
prog = ["C", "Python", "Java", "Go"]
webp = ["HTML", "PHP", "JavaScript"]
myprog = prog + webp
prog[0] = "D"
print(prog)
print(myprog)
plaintext
['D', 'Python', 'Java', 'Go']
['C', 'Python', 'Java', 'Go', 'HTML', 'PHP', 'JavaScript']

리스트 progwebp를 concatenate(연결)하여 myprog에 저장하였다. prog + webp 연산 이후 prog[0] 값을 수정했지만 리스트 myprog에는 영향이 없다.

이번에는 리스트 myprogprog의 값과 "HTML"을 연결하는 연산을 하려고 한다.

python
prog = ["C", "Python", "Java"]
myprog = prog + "HTML"
print(myprog)
plaintext
TypeError: can only concatenate list (not "str") to list

하지만 리스트는 리스트끼리만 연결할 수 있다. int(정수)나 str(문자) 자료형은 리스트와 연결할 수 없기 때문에 myprog = prog + ["HTML"]로 변경해보자

python
prog = ["C", "Python", "Java"]
myprog = prog + "HTML"
myprog = prog + ["HTML"] 
print(myprog)
plaintext
['C', 'Python', 'Java', 'HTML']

리스트 요소 값을 반복하기 위해서는 곱 연산자(*)를 사용한다.

python
prog = ["C", "Python", "Java"]
data = [1, 2, 3]
print(prog * 2)
print(data * 3)
plaintext
['C', 'Python', 'Java', 'C', 'Python', 'Java']
[1, 2, 3, 1, 2, 3, 1, 2, 3]

만약에 리스트끼리 곱한다면 어떻게 될까? print(prog * data)를 실행할 경우 다음과 같은 에러(TypeError)가 발생한다.

TypeError: can't multiply sequence by non-int of type 'list'

리스트 메서드(Method)

리스트는 다양한 메서드를 제공한다. 리스트 메서드는 리스트 객체에 적용할 수 있는 함수이다. 리스트 메서드는 리스트_변수.메서드()의 형태로 사용한다. 다음은 자주 사용하는 리스트 메서드이다.

📍 index()

리스트에서 특정 값의 인덱스를 찾는 메서드이다. 리스트에 해당 값이 없으면 에러(ValueError)가 발생한다.

python
prog = ["C", "Python", "Java", "Go"]
print(prog.index("Java"))
plaintext
2

리스트에 없는 값의 index를 찾으려고 하면 에러가 발생한다.

python
prog = ["C", "Python", "Java", "Go"]
print(prog.index("HTML"))
plaintext
ValueError: 'HTML' is not in list

다음과 같이 대소문자를 변경한 경우는 어떻게 될까?

python
prog = ["C", "Python", "Java", "Go"]
print(prog.index("java"))
plaintext
ValueError: 'java' is not in list

리스트에 있는 값과 대소문자가 다르면 에러가 발생한다. 리스트에 있는 값과 대소문자가 다르면 ValueError가 발생한다.

index()는 대소문자를 구별한다는 것을 기억하자.

append()

리스트의 마지막에 값을 추가하는 메서드이다. 리스트는 자료형의 제한이 없기 때문에 모든 자료형을 추가할 수 있다.

python
a = [1, 2, 3, 4]
b = ["C", "Python", "Java"]
a.append(5)
print(a)
a.append("Go")
print(a)
a.append([6, 7])
print(a)
a.append(b)
print(a)
plaintext
[1, 2, 3, 4, 5]
[1, 2, 3, 4, 5, 'Go']
[1, 2, 3, 4, 5, 'Go', [6, 7]]
[1, 2, 3, 4, 5, 'Go', [6, 7], ['C', 'Python', 'Java']]

↔️ extend()

리스트의 마지막에 값을 추가하는 메서드이다. 하지만 append()와는 다르게 두 개의 리스트를 하나로 합치는 역할을 한다.

python
a = [1, 2, 3, 4]
b = ["C", "Python", "Java"]
a.extend(b)
print(a)
plaintext
[1, 2, 3, 4, 'C', 'Python', 'Java']

info 참고

리스트 a, b와 튜플 c를 사용하여 extend()의 사용 예제를 확인해보자.

python
a = [1, 2]
b = ["C", "Python"]
c = ("a", "b")
메서드결과
a.extend(3)extend()는 리스트끼리 사용하는 함수이다. 왼쪽과 같이 실행할 경우 에러(TypeError)가 발생한다.
TypeError: 'int' object is not iterable
3를 추가하려면 a.extend([3])로 사용해야 한다.
a.extend(b)
[1, 2, 'C', 'Python']
append()와 달리 리스트 요소의 값만 추가한다.
a.append(b)는 다음과 같은 리스트 내에 리스트를 삽입한다.
[1, 2, ['C', 'Python']]
a.extend(c)
[1, 2, 'a', 'b']
extend()는 리스트와 튜플을 연결할 수 있다.
a.append(c)는 다음과 같은 리스트 내에 튜플을 삽입한다.
[1, 2, ('a', 'b')]

🧩 insert()

리스트_변수.insert(인덱스, 값)의 형태로 사용한다. 리스트의 특정 인덱스에 값을 삽입할 수 있다. 인덱스는 0부터 시작하며, 인덱스에 해당하는 값은 뒤로 밀려난다.

python
a = [1, 2, 3, 4]
a.insert(2, 5)
print(a)
plaintext
[1, 2, 5, 3, 4]

📤 pop()

리스트_변수.pop(인덱스)의 형태로 사용한다. 인덱스를 지정하면 리스트에서 해당 인덱스의 값을 삭제하고 삭제한 값을 반환한다. 인덱스를 지정하지 않으면 마지막 요소를 삭제한다. 인덱스가 범위를 벗어나면 에러(IndexError)가 발생한다.

python
a = ["C", "Python", "Java", "Go"]
a.pop()
print(a)
b = a.pop(1)
print(b, a)
plaintext
['C', 'Python', 'Java']
Python ['C', 'Java']

🗑️ remove()

리스트_변수.remove(값)의 형태로 사용한다. 리스트에서 해당 값을 삭제한다. 리스트에 중복된 값이 있을 경우 첫 번째 값만 삭제한다.

python
a = ["C", "Python", "Java", "Go", "Python"]
a.remove("Python")
print(a)
plaintext
['C', 'Java', 'Go', 'Python']

remove()를 사용할 경우 리스트내에 해당 값이 존재하지 않을 경우 에러(ValueError)가 발생한다.

ValueError: list.remove(x): x not in list

info 참고

in 연산자를 사용하여 리스트에 해당 값이 있는지 확인할 수 있다. in 연산자는 리스트에 해당 값이 있으면 True, 없으면 False를 반환한다.

python
a = ["C", "Python", "Java"]
print("Python" in a)
print("Go" in a)
plaintext
True
False

in 연산자를 사용하여 삭제 에러를 방지할 수 있다.

python
a = ["C", "Python", "Java"]
if "Go" in a:
    a.remove("Go")
else:
    print("리스트에 Go가 없습니다.")
plaintext
리스트에 Go가 없습니다.

🔢 count()

리스트_변수.count(값)의 형태로 사용한다. 리스트에서 해당 값이 몇 개 있는지 세는 메서드이다.

python
a = ["C", "Python", "Java", "Go", "Python"]
print(a.count("Python"))
plaintext
2

🔀 sort()

리스트_변수.sort()의 형태로 사용한다. 리스트를 정렬하는 메서드이다. 기본적으로 오름차순으로 정렬한다.

python
a = [7, 9, 5, 1, 4, 8, 3, 2, 6]
a.sort()
print(a)
plaintext
[1, 2, 3, 4, 5, 6, 7, 8, 9]
python
a = [7, 9, 5, 1, 4, 8, 3, 2, 6]
print(a.sort())
plaintext
None

sort()는 리스트 자체를 변경시키기 때문에 다시 되돌릴 수 없다. sort()는 반환 값이 없기 때문에 None이 출력된다.

🔄 reverse()

리스트_변수.reverse()의 형태로 사용한다. 리스트를 역순으로 정렬하는 메서드이다. 리스트를 역순으로 정렬할 때는 sort()와 마찬가지로 리스트 자체를 변경한다. reverse()는 반환 값이 없기 때문에 None이 출력된다.

python
a = [7, 9, 5, 1, 4, 8, 3, 2, 6]
a.reverse()
print(a)
plaintext
[6, 2, 3, 8, 4, 1, 5, 9, 7]

리스트를 내림차순으로 정렬하기 위해 sort()를 적용한 후에 reverse()를 사용하면 내림차순으로 정렬할 수 있다.

python
a = [7, 9, 5, 1, 4, 8, 3, 2, 6]
a.sort()
a.reverse()
print(a)
plaintext
[9, 8, 7, 6, 5, 4, 3, 2, 1]

간결한 코딩을 원한다면 다음과 같이 작성할 수 있다.

python
a = [7, 9, 5, 1, 4, 8, 3, 2, 6]
a.sort(reverse=True)
print(a)
plaintext
[9, 8, 7, 6, 5, 4, 3, 2, 1]

이차원 리스트

리스트 안에 리스트나 튜플(tuple)이 여러 개 있을 때 다음과 같이 리스트로 묶을 수 있다.

python
a = [[1, 2, 3], ["a", "b"], (10, 20, 30)]

리스트 a 안에는 3개의 요소가 있다. 다음 출력문을 통해 이차원 리스트의 요소를 확인해보자.

python
a = [[1, 2, 3], ["a", "b"], (10, 20, 30)]
print(a[0], a[0][1])
print(a[1][1])
print(a[2][1])
plaintext
[1, 2, 3] 2
b
20

a[0][1, 2, 3], a[1]["a", "b"], a[2](10, 20, 30)이다.

print(a[0][1])a[0] 값인 [1, 2, 3]의 인덱스 1에 해당하는 값인 2를 출력한다.

Powered by vitepress-logo-mini