8.1 운영 메모리
운영 메모리 (RAM, 오즈유) 컴퓨터는 고유한 주소를 가지는 메모리 셀 배열로 구성되어 있어. 이 셀들은 숫자, 문자, 포인터 같은 다양한 유형의 데이터를 저장할 수 있어. 프로그램이 실행될 때, 데이터와 명령어를 이 메모리에 배치해서 빠르게 접근할 수 있게 해줘.
메모리 셀의 예:
| 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 |
| 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 |
| 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 |
| 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 |
| 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 |
| 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 |
| 60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 |
| 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 |
각 셀은 고유한 번호를 가지고 있으며, 이걸 메모리 셀의 주소 또는 간단히 주소라고 불러. 예를 들어 컴퓨터에 8GB 메모리가 있으면 80억 개의 셀이 있어서 뭔가 유용한 것을 저장할 수 있어.
비트와 바이트
각 셀은 하나의 바이트 정보를 저장할 수 있어. 각 바이트는 8비트로 구성되어 있고, 각 비트는 0이나 1만 가질 수 있어. 예시 (정수의 경우):
| 숫자 | 비트 표현 | 바이트로 반올림 |
|---|---|---|
| 0 | 0 | 00000000 |
| 1 | 1 | 00000001 |
| 100 | 1100100 | 01100100 |
| 1000 | 1111101000 | 00000011-11101000 |
| 1000 000 000 | 111011100110101100101000000000 | 00111011-10011010-11001010-00000000 |
변수가 차지하는 바이트가 많을수록 더 많은 값을 저장할 수 있어. 예시:
- 1 바이트 — 256가지의 고유한 값
- 2 바이트 — 65,000가지의 고유한 값
- 3 바이트 — 16백만
- 4 바이트 — 4십억
8.2 데이터가 메모리에 표현되는 방법
데이터 타입과 그 표현
숫자 데이터 프로세서 내부와 메모리에서
- 정수: 이진 형태로 저장돼. 크기가 달라질 수 있어 (1 바이트, 2 바이트, 4 바이트).
- 실수: 부동 소수점 형식으로 저장돼 (예: 4바이트와 8바이트 숫자의 IEEE 754 형식).
x = 42 # 정수
y = 3.14 # 실수
중요! Python에서 내장된 int와 float 타입은 무한 길이의 숫자도 처리할 수 있는 완전한 클래스야. 그러나 과학계산이나 AI 라이브러리를 사용할 경우, 아마 내가 설명한 데이터 형식을 만나게 될 거야.
문자 데이터 컴퓨터 메모리에서
문자와 문자열은 메모리에 바이트 시퀀스로 저장돼. 예를 들어, ASCII 인코딩에서는 각 문자가 1 바이트를 차지하고, UTF-8에서는 1부터 4 바이트까지 차지할 수 있어.
Python 3.x에서는 기본적으로 문자열에 UTF-8 인코딩을 사용하지만, 다른 형식으로 저장된 파일을 읽거나 UTF-8이 아닌 인코딩으로 데이터를 전송할 수 있어.
예시:
char = 'A' # 문자
string = "Hello, world!" # 문자열
Python에서 개별 문자는 고유한 타입을 가지지 않고 str 타입을 사용해. 하지만 메모리에서는 문자가 개별적으로 저장돼. 하나의 문자는 보통 1-4 바이트를 차지해.
포인터
포인터는 다른 메모리 셀의 주소를 저장해. 이들은 프로그램이 동적 데이터 구조와의 작업을 더 효율적으로 할 수 있게 해줘.
예시:
list = [1, 2, 3, 4] # 리스트
list_pointer = id(list) # 리스트의 시작 부분에 대한 포인터
8.3 운영 메모리에서의 데이터 표현 예시
1. 정수 표현
정수는 메모리에 이진수(비트)로 저장돼. 데이터 타입에 따라 다양한 바이트 수를 차지할 수 있어. 예를 들어 int는 보통 4 바이트(32 비트)를 차지해.
42 숫자는 메모리에 이렇게 저장될 거야:
| 00000000 | 00000000 | 00000000 | 00101010 |
2. 실수 (부동 소수점) 표현
실수 (예: float 타입)는 주로 IEEE 754 표준에 따라 부동 소수점 형식으로 메모리에 저장돼. float는 보통 4 바이트(32비트)를 차지하며, double은 8바이트(64비트)를 차지해.
중요! 이건 메모리나 프로세서에 기반 한 표준 데이터 타입이야. Python에서의 float 타입은 일반적으로 double 타입과 같고 8바이트를 차지해.
3.14 숫자는 메모리에 이렇게 저장될 거야:
| 01000000 | 01001000 | 11110110 | 01100110 |
3. 문자와 문자열 표현
문자 (예: char 타입)는 메모리에 바이트 시퀀스로 저장돼. 문자열은 문자 배열로 표현돼. C/C++ 언어에서는 문자열이 \0으로 끝나지만 Python에서는 그렇지 않아.
Hello 문자열은 메모리에 이렇게 저장돼:
| 'H' | 'e' | 'l' | 'l' | 'o' |
그리고 이건 0과 1로 이렇게 표현돼:
| 01001000 | 01100101 | 01101100 | 01101100 | 01101111 |
8.4 동적 메모리 주소 지정
동적 메모리는 프로그램 실행 중 필요한 만큼 할당되고 해제돼. Python에서 생성한 모든 객체는 이 메모리에 생성돼.
2가지 유형으로 나뉘어:
힙 (Heap): 동적 객체가 할당되는 메모리 영역이야. C의 malloc 같은 할당 함수 및 C의 free 같은 해제 함수를 통해 이 메모리가 관리돼.
스택 (Stack): 로컬 변수와 함수 호출 데이터를 저장하는 데 사용되는 메모리 영역이야. 함수에 들어갈 때와 나올 때 메모리가 자동으로 할당되고 해제돼.
다시 말하지만, Python은 너무 고수준의 언어이기 때문에 이런 예제를 보여줄 수 없어. 대신 C 언어 예제를 줄 수 있어:
// 10개의 정수로 이루어진 배열에 대한 동적 메모리 할당
int *dynamic_var = (int *)malloc(sizeof(int) * 10);
// 메모리 해제
free(dynamic_var);
메모리 주소 지정은 각 메모리 셀에 고유한 주소를 할당하는 과정이야. 각 주소는 데이터나 명령어를 포함할 수 있는 메모리의 특정 위치를 가리켜.
주소 지정 유형
물리적 주소 지정: 메모리 셀의 물리적 주소에 직접 접근하는 것. 메모리 컨트롤러 같은 하드웨어에 의해 관리돼.
가상 주소 지정: 페이징 메모리나 세그먼트 메모리 같은 메모리 관리 메커니즘을 사용하여 프로세스에 독립적이고 보호된 주소 공간을 제공해.
GO TO FULL VERSION