[Jungle][TIL] 240423 C 포인터 | 메모리 주소 계산

somi·2024년 4월 23일
0

[Krafton Jungle]

목록 보기
37/68
1. #include <stdio.h>

2	int main() 
3	{
4	
5		int numArr[5] = { 11, 22, 33, 44, 55 }; 
6		int *numPtrA; 
7		void *ptr;
8		numPtrA = &numArr[2];  
9		ptr = numArr;
10		printf("%d\n", *(numPtrA + 2));
11		printf("%d\n", *((int *)ptr + 1));
12	
13	
14	return 0; 
15	
16	}

* : 포인터 변수 주소값에 있는 데이터를 가리킨다.
* 연산자는 포인터를 역참조하여 해당 포인터가 가리키는 메모리에 저장된 값을 가져오게 된다.!
& : 변수의 주소값을 불러 온다. !!

numPtrA는 numArr[2] => 33 의 주소를 가리킴

numPtrA 는 33을 가리키는 포인터
=> *(numPtrA + 2) => 55를 가리키는 포인터가 된다.

*((int *)ptr + 1)
=> 포인터 ptr을 int 포인터로 형변환 후
ptr이 가리키는 주소에서 포인터 주소 1만큼 떨어진 곳에 있는 값을 역참조하여 가져온다. => 22

*(++(int*)ptr)도 같다. 전위 연산자를 사용해서 +1을 해준 것


2차원 배열의 포인터


c언어 변환 문자 의미 자료형

%d : 10진수로 출력 정수형
%f : 실수형
%e : 지수형
%o : 8진수로 출력
%x : 16진수로 출력
%u : 부호없는 10진수로 출력
%g : 실수형으로 자동 출력
%p : 포인터의 주소를 출력
%c : 하나의 문자로 출력 문자형
%s : 문자열을 출력

=>

#include <stdio.h>
int main() {
  char* str[2]; str[0] = "hello!"; 
  str[1] = "jungler";
  printf("1. %s\n", str[0] + 1); 
  printf("2. %s\n", (str + 1)[0] + 2);
  return 0; 
  
}

str[0] + 1 -> hello에서 e를 가리키는 포인터이다.
따라서 1. ello! 가 출력된다.
(str + 1)[0] + 2 => j를 가리키는 포인터 + 2만큼 이동 => n를 가리키는 포인터 => 2. ngler 가 출력된다.


AVL 트리의 삽입

삽입 후에 불균형 상태가 되었다면,
불균형 상태가 된 ( 균형 인수의 절댓값이 2 이상이 된 ) 노드 중에서, 삽입 위치에서 가장 가까운 조상 노드(A)의 부분트리를 조정하는 재균형 연산이 별도로 필요

재균형 연산은 A를 중심으로 회전함으로써 진행


%p

printf에서 %p는 포인터 변수가 가리키는 객체의 메모리 주소를 16진수 형태로 출력하게 해주는 format specifier

#include <stdio.h>

int main()
{
    int num1 = 10;

    printf("%p\n", &num1);    // num1의 메모리 주소를 출력
                              // 컴퓨터마다, 실행할 때마다 달라지게 된다. 

    return 0;
}

예시) 008AF7FC 이런 형태로 출력된다.

32비트, 64비트와 메모리 주소

시스템이 32비트인지 64비트인지에 따라 메모리 주소의 범위도 달라짐.
32비트: 16진수 8자리
0x00000000 ~ 0xFFFFFFFF
예) 0x008AF7FC
64비트: 16진수 16자리
0x0000000000000000 ~ 0xFFFFFFFFFFFFFFFF
예) 0x00000000008AF7FC
64비트 메모리 주소는 0x00000000`00000000처럼 8자리씩 끊어서 표기하기도 한다.
앞으로 16진수 8자리 또는 16자리로 된 숫자가 나오면 일단 메모리 주소라 생각하면 된다.

c언어 자료형별 할당되는 메모리 크기

  1. 2자리 이동한거니까 0x8004000fd5
    배열 요소가 1바이트씩 증가 => 2바이트 이동한 위치가 된다.

  2. arr_int가 가리키는 포인터의 위치와 arr_int[0]이 가리키는 포인터는 같다. => 0x8004000fbc

  3. 시스템이 64비트인 경우 int_64 타입의 요소의 크기는 8바이트이다.
    int 32비트의 경우 int는 4바이트를 가진다.
    => arr_int64의 시작 위치에서 8*3 => 24바이트 이동한 위치가 arr_int64[3]이 가르키는 위치이다.

18 은 16진수로 표현된 24
24÷16=1(몫), 나머지=8
위에서 구한 나머지 8을 16진수로 표현하면 8이 됩니다. (16진수에서 8은 그대로 8입니다.)
다음으로, 몫인 1을 16으로 나눕니다.
1÷16 = 0(몫) , 나머지 = 1
이제 마지막 남은 나머지 1을 16진수로 표현하면 1

=> 역순으로 합쳐셔
0x18이 된다.

마지막 자릿수인 0x90에서 24바이트 증가하면 0xa8이 된다
=> 0x8004000fa8가 된다.


참고)
https://dojang.io/mod/page/view.php?id=274

profile
📝 It's been waiting for you

0개의 댓글