! 지금까지 숫자형, 문자열, 리스트, 튜플, 딕셔너리, 집합, 불 자료형에 대해서 알아보았다.
a, b, name과 같은 것들을 계속 사용해 왔다.파이썬에서 변수를 만들 때는
=기호를 사용한다.
>>> a = 1
>>> b = "python"
>>> c = [1, 2, 3]
a, b, c가 변수이다.a → 1
b → "python"
c → [1, 2, 3]
변수를 만드는 기본 형태는 다음과 같다.
변수명 = 값
예를 들어
age = 20
name = "pingu"
numbers = [1, 2, 3]
와 같이 사용할 수 있다.
=는 같다는 뜻일까?수학에서는
=가 두 값이 같다는 의미로 사용된다.
1 + 1 = 2
=는 대입(assignment)이라는 의미이다.a = 10
은
a와 10이 같다.
라는 의미보다는
a라는 변수에 10이라는 값을 연결한다.
라고 이해하는 것이 좋다.
두 값이 같은지 비교할 때는
==를 사용한다.
>>> a = 10
>>> a == 10
True
| 기호 | 의미 |
|---|---|
= | 값을 변수에 대입 |
== | 두 값이 같은지 비교 |
다른 프로그래밍 언어에서는 변수를 만들 때 자료형을 먼저 지정하는 경우가 있다.
예를 들어 어떤 언어에서는 다음과 같은 형태를 사용하기도 한다.
정수형 변수 a = 10
문자열 변수 name = "python"
하지만 파이썬에서는 변수에 값을 저장하면 파이썬이 그 값의 자료형을 알아서 판단한다.
a = 10
name = "python"
numbers = [1, 2, 3]
a → 정수형name → 문자열numbers → 리스트>>> type(a)
<class 'int'>
>>> type(name)
<class 'str'>
>>> type(numbers)
<class 'list'>
따라서 파이썬에서는 변수의 자료형을 미리 선언할 필요가 없다.
변수 이름을 마음대로 만들 수 있는 것처럼 보이지만 몇 가지 규칙을 지켜야 한다.
변수명에는 기본적으로 다음과 같은 문자를 사용할 수 있다.
영문자
숫자
언더스코어(_)
예를 들어 다음은 올바른 변수명이다.
name = "pingu"
age = 20
user_name = "pingu"
count1 = 10
_private = "private"
변수 이름에 숫자를 사용할 수는 있지만 첫 번째 글자가 숫자이면 안 된다.
name1 = "pingu" # 가능
user2 = "python" # 가능
다음은 사용할 수 없다.
1name = "pingu" # 오류
2user = "python" # 오류
간단하게 기억하면 다음과 같다.
name1 → O
1name → X
다음과 같이 변수명을 만들면 안 된다.
user-name = "pingu"
-는 파이썬에서 뺄셈 연산자로 사용되기 때문이다.대신 언더스코어
_를 사용할 수 있다.
user_name = "pingu"
user-name → X
user_name → O
파이썬에서는 대문자와 소문자를 서로 다른 문자로 판단한다.
name = "pingu"
Name = "python"
NAME = "hello"
name
Name
NAME
파이썬은 대소문자를 구분한다.
파이썬에는 특별한 기능을 수행하기 위해 미리 정해져 있는 단어들이 있다.
대표적으로 다음과 같은 단어들이 있다.
if
else
for
while
and
or
not
True
False
None
def
class
import
return
예를 들어 다음처럼 사용할 수 없다.
if = 10
for = "python"
if, for는 파이썬 문법에서 이미 특별한 의미를 가지고 있기 때문이다.파이썬에서 어떤 단어가 예약어인지 확인하려면
keyword모듈을 이용할 수도 있다.
>>> import keyword
>>> keyword.kwlist
아직
import나 모듈을 배우지 않았다면 지금은 파이썬 문법에서 사용하는 특별한 단어를 변수명으로 사용할 수 없다 정도만 기억하면 된다.
문법적으로 사용할 수 있다고 해서 아무 이름이나 사용하는 것이 좋은 것은 아니다.
예를 들어 다음 코드를 보자.
a = 25
b = 95
c = "김철수"
a, b, c가 무엇을 의미하는지 알기 어렵다.다음처럼 의미를 알 수 있는 변수명을 사용하는 것이 좋다.
student_age = 25
total_score = 95
student_name = "김철수"
파이썬에서는 여러 단어를 이용해 변수명을 만들 때 보통 snake_case 방식을 많이 사용한다.
student_name
user_age
total_score
login_count
_로 연결한다.student + name
↓
student_name
다음과 같이 의미가 명확한 변수명을 사용하는 습관을 들이는 것이 좋다.
user_name = "pingu"
user_age = 20
total_price = 50000
login_count = 3
지금까지는 변수를 단순히 값을 저장하는 공간이라고 생각했다.
하지만 파이썬에서는 조금 더 정확하게 말하면
변수는 객체를 가리킨다.
라고 할 수 있다.
객체라는 말이 처음에는 어렵게 느껴질 수 있다.
지금까지 우리가 사용했던 다음 값들도 모두 파이썬에서는 객체이다.
1
"python"
[1, 2, 3]
{'name': 'pingu'}
등의 데이터들이 메모리에 만들어지고 변수는 그 객체를 가리킨다.
변수를 이름표라고 생각하면 이해하기 쉽다.
다음 코드가 있다고 해 보자.
a = [1, 2, 3]
이를 단순하게 생각하면
a
↓
[1, 2, 3]
와 같은 관계가 된다.
[1, 2, 3]이라는 리스트 객체가 만들어진다.a라는 변수가 그 객체를 가리킨다.변수 a
│
▼
[1, 2, 3]
즉, 변수
a는[1, 2, 3]자체라기보다는[1, 2, 3]이라는 객체를 가리키는 이름표라고 생각할 수 있다.
프로그램에서 사용하는 데이터는 컴퓨터의 메모리에 저장된다.
예를 들어
a = [1, 2, 3]
을 실행하면 [1, 2, 3]이라는 리스트 객체가 메모리에 만들어진다.
파이썬에서는
id()함수를 이용해서 객체를 식별하는 값을 확인할 수 있다.
>>> a = [1, 2, 3]
>>> id(a)
결과는 실행 환경에 따라 다음과 같은 숫자로 나타날 수 있다.
4303029896
이 숫자는 컴퓨터나 실행할 때마다 달라질 수 있으므로 숫자 자체를 외울 필요는 없다.
id()는 두 변수가 같은 객체를 가리키고 있는지 확인할 때 유용하다.
>>> a = [1, 2, 3]
>>> b = a
>>> id(a)
4303029896
>>> id(b)
4303029896
id(a) == id(b)
a와 b가 같은 리스트 객체를 가리키고 있다는 뜻이다.리스트를 사용할 때 초보자가 가장 많이 헷갈리는 부분 중 하나이다.
다음 코드를 보자.
>>> a = [1, 2, 3]
>>> b = a
처음 보면 다음처럼 생각하기 쉽다.
a의 리스트를 복사해서 b에 넣었다.
하지만 정확하게는 그렇지 않다.
b = a를 실행하면 새로운 리스트가 만들어지는 것이 아니다.
┌───────────┐
a ─────▶│ [1, 2, 3] │
└───────────┘
▲
│
b ───────────┘
a와 b가 같은 리스트 객체를 가리키게 된다.따라서 다음과 같이 확인할 수 있다.
>>> a = [1, 2, 3]
>>> b = a
>>> id(a) == id(b)
True
is를 사용하면 두 변수가 동일한 객체를 가리키는지 확인할 수 있다.
>>> a = [1, 2, 3]
>>> b = a
>>> a is b
True
True이므로 a와 b는 같은 객체를 가리킨다.여기서
==와is의 차이에 주의하자.
==
→ 값이 같은가?
is
→ 실제로 같은 객체인가?
예를 들어
a = [1, 2, 3]
b = [1, 2, 3]
라고 하면 두 리스트의 값은 같다.
>>> a == b
True
하지만 각각 따로 만든 리스트이므로 같은 객체는 아닐 수 있다.
>>> a is b
False
! ==와 is의 차이
== → 내용이 같은지 확인 is → 같은 객체를 가리키는지 확인
다음 코드를 실행해 보자.
>>> a = [1, 2, 3]
>>> b = a
이 상태에서 a의 값을 수정한다.
>>> a[1] = 4
>>> a
[1, 4, 3]
그렇다면
b는 어떻게 되었을까?
>>> b
[1, 4, 3]
b를 직접 수정하지 않았는데도 값이 바뀌었다.그 이유는
a와b가 같은 리스트를 가리키고 있기 때문이다.
수정 전
a ───┐
▼
[1, 2, 3]
▲
b ───┘
a[1] = 4를 실행하면
a ───┐
▼
[1, 4, 3]
▲
b ───┘
a와 b 모두 그 리스트를 보고 있기 때문에 둘 다 변경된 것처럼 보인다.! 중요
b = a는 리스트의 내용을 새로 복사하는 것이 아니라
a와 b가 같은 객체를 가리키도록 만드는 것이다.
그렇다면
a의 값을 복사해서b를 만들되, 두 리스트가 서로 영향을 주지 않게 하려면 어떻게 해야 할까?
대표적으로 다음 방법을 사용할 수 있다.
1. 슬라이싱 [:]
2. copy()
리스트 전체를 슬라이싱하면 새로운 리스트를 만들 수 있다.
>>> a = [1, 2, 3]
>>> b = a[:]
a[:]는 리스트 a의 처음부터 끝까지 가져온다.이제
a를 수정해 보자.
>>> a[1] = 4
>>> a
[1, 4, 3]
>>> b
[1, 2, 3]
a만 변경되었다.b는 영향을 받지 않는다.그 이유는 서로 다른 리스트 객체를 가리키고 있기 때문이다.
a ─────▶ [1, 4, 3]
b ─────▶ [1, 2, 3]
>>> a is b
False
False이므로 서로 다른 객체이다.따라서 리스트를 별도로 복사하고 싶다면 다음과 같이 사용할 수 있다.
b = a[:]
리스트를 복사하는 또 다른 방법은
copy()를 사용하는 것이다.
>>> a = [1, 2, 3]
>>> b = a.copy()
>>> b
[1, 2, 3]
하지만
>>> a is b
False
따라서
a를 수정해도b에는 영향을 주지 않는다.
>>> a[0] = 10
>>> a
[10, 2, 3]
>>> b
[1, 2, 3]
파이썬의
copy모듈을 이용하는 방법도 있다.
>>> from copy import copy
>>> a = [1, 2, 3]
>>> b = copy(a)
>>> b is a
False
아직
from,import, 모듈을 배우지 않았다면 지금은 다음 정도로 이해하면 된다.
b = copy(a)
는 리스트를 별도의 객체로 복사하기 위한 방법 중 하나이다.
지금까지 살펴본 방법은 다음과 같다.
b = a[:]
b = a.copy()
from copy import copy
b = copy(a)
초보 단계에서는 다음 두 방법이 가장 간단하다.
b = a[:]
또는
b = a.copy()
b = a와 b = a.copy() 차이| 코드 | 같은 객체? | a 수정 시 b 영향 |
|---|---|---|
b = a | O | O |
b = a[:] | X | X |
b = a.copy() | X | X |
! 리스트 복사 핵심
b = a→ 같은 리스트를 함께 사용
b = a.copy()→ 새로운 리스트를 만들어 복사
파이썬에서는 변수에 값을 대입하는 방법이 여러 가지 있다.
다음과 같이 한 줄에서 여러 변수에 값을 저장할 수 있다.
>>> a, b = ('python', 'life')
>>> a
'python'
>>> b
'life'
튜플은 괄호를 생략할 수 있기 때문에 다음처럼 작성하는 경우가 더 많다.
>>> a, b = 'python', 'life'
a → 'python'
b → 'life'
리스트를 이용해서도 여러 변수에 값을 대입할 수 있다.
>>> [a, b] = ['python', 'life']
>>> a
'python'
>>> b
'life'
a ↔ 'python'
b ↔ 'life'
여러 개의 변수에 동시에 같은 값을 저장할 수도 있다.
>>> a = b = 'python'
>>> a
'python'
>>> b
'python'
a와 b 모두 'python'을 가리키게 된다.숫자에서도 사용할 수 있다.
x = y = z = 0
x → 0
y → 0
z → 0
파이썬에서는 두 변수에 저장된 값을 매우 간단하게 서로 바꿀 수 있다.
먼저 다음 값을 저장해 보자.
>>> a = 3
>>> b = 5
현재 상태는 다음과 같다.
a → 3
b → 5
다음 한 줄을 실행한다.
>>> a, b = b, a
결과를 확인해 보자.
>>> a
5
>>> b
3
변경 전
a → 3
b → 5
a, b = b, a
변경 후
a → 5
b → 3
a, b = b, a를 다음처럼 생각하면 이해하기 쉽다.
오른쪽의 값을 먼저 묶는다.
b, a
현재 값은
5, 3
이다.
그 후 왼쪽 변수에 각각 대입한다.
a ← 5
b ← 3
따라서 두 값이 서로 바뀐다.
다른 언어에서는 값을 바꾸기 위해 임시 변수를 사용하는 경우가 있다.
예를 들어 개념적으로 다음과 같이 할 수 있다.
temp = a
a = b
b = temp
하지만 파이썬에서는
a, b = b, a
한 줄로 처리할 수 있다.
이번 장에서 가장 중요한 내용을 정리하면 다음과 같다.
=를 사용해서 만든다.a = 10
=는 대입 연산자이다.= → 값 대입
== → 값 비교
a = 10
b = "python"
c = [1, 2, 3]
name1 = "pingu" # O
1name = "pingu" # X
_를 사용하는 snake_case 방식이 많이 사용된다.user_name
total_score
login_count
if
for
while
class
등을 변수명으로 사용할 수 없다.
a = [1, 2, 3]
a ─────▶ [1, 2, 3]
id()를 이용하면 객체의 식별 값을 확인할 수 있다.id(a)
is는 두 변수가 같은 객체를 가리키는지 확인한다.a is b
b = a는 리스트 자체를 새로 복사하는 것이 아니다.a = [1, 2, 3]
b = a
a ───┐
▼
[1, 2, 3]
▲
b ───┘
a를 수정하면 b에서도 변경된 값이 보인다.>>> a[0] = 10
>>> a
[10, 2, 3]
>>> b
[10, 2, 3]
b = a[:]
또는
b = a.copy()
a, b = 'python', 'life'
a = b = 10
a, b = b, a
! 변수에서 가장 중요한 핵심
변수를 단순히 값을 담는 상자라고 생각해도 처음에는 충분하다.
하지만 리스트 복사를 이해하려면 한 단계 더 나아가 다음 개념을 기억해야 한다.
변수 = 객체에 붙여 놓은 이름표따라서
a = [1, 2, 3] b = a는 리스트가 2개 만들어지는 것이 아니다.
a ───┐ ▼ [1, 2, 3] ▲ b ───┘a와 b라는 2개의 이름표가 하나의 리스트 객체를 같이 가리키는 것이다.
반대로 서로 별도의 리스트가 필요하다면
b = a[:]또는
b = a.copy()와 같이 복사해야 한다.
이번 장에서는 특히
b = a → 같은 객체 b = a.copy() → 서로 다른 객체이 차이를 확실하게 기억해 두자.