[Python] 1.1 Python 수 자료형

정수형(Integer)


정수를 다루는 자료형, +, -, 0. 코딩 테스트에서는 대부분이 정수형 입출력을 다루는 문제들

실수형(Real Number)


소수점 아래의 데이터를 포함하는 수 자료형. 파이썬에서는 변수에 소수점을 붙인 수를 대입하면 실수형 변수로 처리한다.

정수부가 0인 소수는 0을 생략하고 작성할 수 있다

a = -.7     # -0.7

소수부가 0이면 생략가능하다

a = 5.      # 5.0

e나 E를 이용한 지수 표현 방식을 이용할 수 있다.

유효숫자*e^지수 = 유효숫자 * 10^지수

도달할 수 없는 최대값(INF)를 표현할 때 유용하다

1e9       # 10억 == 100000000.0

round()


실수형을 정수형으로 반올림 해주는 함수

a = 0.3 + 0.6
print(a)
>>> 0.899999999
print(round(a, 4))
>>> 0.9

기본 연산


사칙연산은 +, -, *, / 를 통해 연산한다.

여기서 /는 주의가 필요하다. 결과를 실수형으로 처리하기 때문에

a = 7
b = 3
print(a / b)       # 정수 / 정수 = 실수
>>> 2.333333333335
print(a % b)       # 나머지(정수)
>>> 1
print(a // b)      # 몫(정수)
>>> 2
print(a ** b)      # 거듭제곱: 7의 3승
>>> 343

리스트 자료형


파이썬은 C, Java와 같은 언어의 배열(Array)기능을 포함한다. 내부적으로 리스트 자료구조를 채택하고 있어서 append(), remove()등의 메서드를 지원한다.

C++의 STL vector와 유사하다.

배열, 테이블이라고 부르기도 한다.

리스트 생성


a = [1, 2, 3, 4, 5, 6, 7, 8, 9]
print(a)
>>> [1, 2, 3, 4, 5, 6, 7, 8, 9]
print(a[4])     # index 4에 접근
>>> 5           # index는 0부터 시작하므로 5
b = list()      # 빈 리스트 생성 2가지 방법
c = []
print(b)
>>> []
print(c)
>>> []

코딩테스트에서는 주로 크기가 N인 1차원 리스트를 많이 사용한다. 따라서 초기화해야 할 경우 아래와 같은 방법으로 하면 좋다

# 크기가 N인 input
N = 10
arr = [0] * N     # 크기가 N, 모든 원소의 값은 0
print(arr)
>>> [0, 0, 0, 0, 0, 0, 0, 0, 0, 0]

리스트 인덱싱 & 슬라이싱


인덱싱(Indexing)이란 index값을 이용하여 특정한 원소에 접근하는 것

파이썬은 특이하게 음의 정수로 인덱싱을 할 수 있다.

a = [1, 2, 3, 4, 5]
print(a[-1])       # 뒤에서 첫 번째
>>> 5
print(a[-3])       # 뒤에서 세 번째
>>> 3
a[0] = 100         # 첫 번째 원소값 변경
print(a)           # index의 시작은 0부터
>>> [100, 2, 3, 4, 5]

슬라이싱(Slicing)이란 리스트에서 특정 부분을 잘라서 가져오는 것, 콜론을 이용한다

인덱싱이 헷갈릴 수 있으니 주의한다.

a = [1, 2, 3, 4, 5]
# 두 번째 원소부터 네 번째 원소까지
print(a[1:4])
>>> [2, 3, 4]

리스트 컴프리헨션(List Comprehension)


리스트 컴프리헨션은 리스트를 초기화 하는 방법 중 하나이다.

대괄호 안에 조건문과 반복문을 넣는 방식으로 리스트를 초기화 할 수 있다

# 0 ~ 19까지의 수 중 홀수만 포함하는 리스트
arr = [i for i in ragne(20) if i % 2 == 1]
print(arr)
>>> [1, 3, 5 ,7, 9, 11, 13, 15, 17, 19]

# 1~9의 제곱값을 포함하는 리스트
arr = [i*i for i in range(1, 10)]
print(arr)
>>> [1, 4, 9, 16, 25, 36, 49, 64, 81]

N x M 크기의 2차원 배열을 초기화 할 때도 유용하게 사용된다

N = 3
M = 5
arr = [[0] * M for _ in range(N)]
print(arr)
>>> [[0, 0, 0, 0, 0], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0]]

2차원 배열 할당시 주의할점!!

2차원 배열에는 무조건 리스트 컴프리헨션을 사용한다.

arr = [[0] * M] * N
arr[1][1] = 5
print(arr)
>>> [[0, 5, 0, 0, 0], [0, 5, 0, 0, 0], [0, 5, 0, 0, 0]]

위와 같이 의도치 않은 결과가 나올 수 있다.

내부적으로 포함된 3개의 리스트가 모두 동일한 객체에 대한 레퍼런스로 인식되기 때문이다.

리스트 관련 메서드


  • append(): 리스트에 원소 하나 삽입할 때 사용한다. O(1)
  • sort(): 오름차순으로 정렬한다. O(NlogN)
  • sort(reverse=True): 내림차순으로 정렬한다. O(NlogN)
  • reverse(): 리스트의 원소 순서를 뒤집는다. O(N)
  • insert(): 특정한 인덱스 위치에 원소를 삽입한다. O(N)
  • count(): 특정한 값을 갖는 데이터의 개수를 셀 때 사용한다. O(N)
  • remove(): 특정한 값을 가진 원소를 제거한다. 해당 값이 여러개면 하나만 제거한다. O(N)

insert와 append모두 원소의 추가에 사용된다. 하지만 시간복잡도는 다르다. insert를 남용할 경우 “시간 초과”가 발생할 확률이 높다.

remove는 원소 하나만 지우는 메서드이다. 그렇다면 해당 값을 가진 모든 원소를 지우려면 O(N)을 반복적으로 호출하게 된다. 이를 방지하기위해 다음과 같이 리스트 컴프리헨션을 사용하면 좋다.

a = [1, 2, 3, 4, 5, 5, 5]
remove_set = {3, 5}

# remove_set에 포함되지 않은 값만을 저장
result = [i for i in a if i not in remove_set]
print(result)
>>> [1, 2, 4]

반복적인 remove의 호출을 피할 수 있어서 수행시간이 단축된다.