창조유저그룹-커즈닷컴
Window close
ID :     PASS :   
   
  처음으로
  창조
  창조 소개
창조 다운로드
CUGz.com 소개
온라인 도움말
  커뮤니티
  가입인사
자유게시판
Q/A게시판
TIP/TECH
열린강좌
자주하는질문
아이디어게시판
  자료실
  소스자료실
프로그램자료실
기타자료실
명예의 전당
이미지 자료실
  지원/기타
  표준용어재정
구글 웹서치  
관리자 전용


LIST ALL
Posted by 지상현2005-01-01 13:49:56, Hit : 5622
[re] [ps.구루 강좌 #12♭]포인터를 왜 씁니까?
Homepage : http://myhome.naver.com/bc88c
Post URL : http://cugz.sjworks.net/bbs/zboard.php?id=open_lec&no=59

하나만 더 남기도록 하겠습니다.

이제서야 포인터를 아는 저로서는, 포인터라는 놈이 얼마나 편한지
반은 알고 있으므로-_- 그 편함을 같이 나누고 싶어서-_- 말이죠...






제가 봐도 너무 말이 안되는 내용이네요.
맨 밑에, 예를 든 것만 보셔도 무방할 듯 싶습니다.










구조체를 사용하는데 있어서 포인터를 왜 사용하느나면,
TDummy 라는, 크기가 1024 바이트인 구조체가 있다고 가정합시다. -_-;


어떤 루틴에서, 저 구조체를 인자로 받아들일 때 포인터가 아닌, 구조체 자체를 받는다고 치면

예) procedure comeonStructure(const a: TDummy); // 이런 문법이 먹힐는지는 모르겠지만

어쨌든 저 프로시저를 호출하면서, TDummy 라는 구조체를 하나 넘겨야 할테죠.
구조체의 포인터가 아닌, 구조체 자체를 넘긴다고 칩시다.

그 전에, 하나 예를 더 들어보겠습니다.

procedure b;
var
    k: integer;
begin
  //...
end;

procedure a;
var
    k: integer;
begin
    b;
end;

저런 프로시저들이 있다고 하면...
a에도, b에도 k라는 변수가 있습니다.
하지만 그건 서로 다른 변수도, 각 함수에서 다른 쪽의 k에 접근할 수 없다는 것은(문법적으로) 분명한 일이죠?

스택이란 놈이 있어서 가능한 일인데요. 재귀호출도 스택이 있어서 가능합니다.



이제부터 중요합니다. -_-;
일단 컴퓨터라는 놈은 메모리의 데이터를 가르키기 위해 주소를 사용합니다.(지금은 포인터랑 별개의 것이라고 생각해 주세요.)

procedure comeonStructure(const a: TDummy)
begin
// 일하기
end;

procedure myProc;
var
    data: TDummy;
begin
comeonStructure(data);
end;

뭐 이런 코드가 있다고 생각합시다.

하나 하나 생각해보죠.
먼저, myProc 부터 시작합시다.
var에 data: TDummy;가 있으므로, myProc 함수의 스택에 새로운 TDummy 를 할당합니다.
아까 TDummy는 1024 바이트라고 했으므로, 1024 바이트만큼 공간을 차지하겠죠. 그리고, 이번에 할당된 TDummy 의 주소는 0 이라고 해둡시다.

그리고, comeonStructure(data); 로, comeonStructure 함수를 호출하겠습니다.
여기서 중요합니다. 스택이라는 놈 때문에(자세한 동작은 모르겠습니다), 메모리에다가 인자를 하나 하나 차례로 넣습니다(push). 그리고 실행위치를 comeonStructure 함수의 주소로 옮깁니다. 그러면 comeonStructure 함수는 다시 스택에서 반대의 순서로 데이터를 꺼내옵니다(pop).

어셈을 조금 해보셨으면 쉽게 이해가 가실겁니다.
컴퓨터에서 함수란 개념은 단순히 실행 위치를 여기서 저기로 옮기는 것이고, 이 때 "인자"란 것을 구현하기 위해 저렇게 동작합니다.

즉 호출하는 쪽에서 인자들을 순서대로 스택에 넣고, 호출하는 곳으로 이동하면, 호출하는 곳은 인자를 반대의 순서대로 꺼내서 사용하는거죠.

접시를 쌓는 예에서 생각해봅시다.
제가 구루님께-_- 빨간 접시, 파란 접시, 노란 접시를 넘겨 드려야 합니다. 순서대로요.
그러면 저는 테이블에 노란 접시, 파란 접시, 빨간 접시의 순서대로 접시를 쌓아놓고 사라집니다.
그러면 구루님께서는 나중에 나타나셔서, 위에서부터 빨간 접시, 파란 접시, 노란 접시의 순으로 가져가서 사용하시는 거죠.

뭐 이런 식입니다. -_-

잠시 딴데로 흘렀는데, 아까 그 함수들의 예를 보면
일단 myProc 는 comeonStructure를 호출하기 위해, 인자들을 스택 메모리에 넣습니다.
이 때 구조체 자체를 넘긴다면, TDummy 라는 데이터를 새로이 넣습니다.
즉 스택에는 또다시 1024 바이트 만큼 공간이 할당되고, "data: TDummy"의 내용이 새로 만들어진 공간으로 복사됩니다.
그리고 comeonStructure 에서는, a: TDummy; 때문에 내부적으로 1024 바이트 만큼 공간을 할당합니다. 그리고 스택에서 인자를 가져옵니다. 이 때 또 1024 바이트 낭비됩니다.

이해가 가셨나요?
구조체 자체를 인자로 넘기면, 넘길 때 1번, 받을 때 1번... 쓸모 없게 2번이나 메모리 공간이 낭비되고, 쓸데없이 CPU를 사용합니다(구조체를 비트 복사할 때).

이런 비효율적인 상황을 타개하기 위해, 포인터를 써 봅시다.

procedure comeonStructure(a: TDummy^)
begin
// a를 그대로 씁니다
end;

procedure myProc;
var
    data: TDummy;
begin
    comeonStructure(@data);
end;

자...일단 이해를 쉽게 하기 위해 C 스타일로 했습니다.
델파이라면 var a:TDummy 로 받고, data 를 넘겨주면 되겠죠?

일단, myProc에 data: TDummy 만큼 1024 바이트의 메모리가 할당됩니다.
그리고 할당된 메모리의 주소(아까 0이라고 했죠)를 넘깁니다. 32비트 운영체제에선 4바이트입니다.
벌써부터 아까랑 다르네요. 아까는 무식하게 1024 바이트를 새로 할당해서 넣었지만, 지금은 단지 4바이트를 넣었습니다.
호출받는 쪽 comeonStructure 에서도, (포인터형이니까) 4바이트만 받습니다.
그리고 그 포인터 안에 있는 내용은 아까 data: TDummy;의 주소, 즉 0 이겠죠.
그럼 comeStructure에선 그 구조체를 그냥 쓰면 됩니다.

아까랑 너무 다르네요-_-
이런 식입니다. 그래서 구조체는 가능한한 포인터를 사용합니다.
LongInt 같은 숫자는, 값으로 넘기나(4바이트), 포인터로 넘기나(지금 컴퓨터에서 4바이트) 똑같으니까 별 문제는 없습니다.
다만 값으로 넘기면, 넘겨받은 쪽이 그 값을 마음대로 조리해도 새로 할당된 메모리의 것이 바뀌니까 원본에는 문제가 없지만, 포인터로 넘겼을 때 마음대로 조리하면 원본도 바뀌는게 다르달까요?







마지막으로, 예를 들어 깔끔하게(?) 마무리 했으면 좋겠네요. -_-

제가 구루님께 김치(?)를 드리려고 합니다. -_-; 이 김치는 TDummy 안에 있는 멤버 중 하나입니다.
그래서 제가 구루님 계신 곳으로 냉장고(TDummy)를 낑낑대며 들고갑니다.(새로이 메모리를 할당하여 그곳에 복사)
그리고 냉장고에서 김치를 꺼내, 구루님께 드리는거죠. -_-
그리고 다시 낑낑대며 가져갑니다.(메모리 복구)


이런 상황이 바로 구조체를 직접 넘기는 짓입니다. 포인터를 사용한다면

저는 구루님께 냉장고의 위치를 알려드리고, 구루님은 그저 그 김치를 꺼내가면 됩니다.

대충 이런식이 됩니다. 예는 너무 믿지 마세요. 그냥 작업 자체가 얼마나 비효율/효율적인가만 나타내려고 말도 안되는 예를 들었습니다. -_-;

포인터를 쓰면 확실히 작업이 편하고(경우에 따라 다르지만-_-) 효율적이 됩니다.
그렇지만 한편으론 포인터가 있어서 Access Violation 같은 사람 환장하게 하는 버그가 생기지만요-_-;


ps.이진백   2005-01-02 AM 9:04:42  
잘 가르쳐주셔서 고맙습니다.
LIST ALL               GO TO THE TOP


N
   Subject
Posted by
Date
H
69
   리소스 해커를 이용하여 DLL 파일안의 HTML 문서 넣기! [4]
qkrwhdgns 2005/07/20  5663
68
   [끼적강좌 8]RPG게임을 만들어보자 [1강] [3]
권선중 2005/07/16  6065
67
     [re] [끼적강좌 8]RPG게임을 만들어보자 [2강] [1]
권선중 2005/07/17  5694
66
   [끼적강좌7] 달력 구현강좌 [1강][초급]
권선중 2005/07/11  5146
65
     [끼적강좌7] 달력 구현강좌 [2강][고급]
권선중 2005/07/15  4850
64
       [끼적강좌7] 달력 구현강좌 [3강][응용]
권선중 2005/07/16  4633
63
   [끼적강좌 6] 선중이 계발한 암호화구현 [7]
권선중 2005/06/29  4860
62
   [끼적 강좌] 기본문법을 알아야 한다...! [10]
권선중 2005/06/27  4922
61
   [끼적강좌 5] 로그인 구현강좌 [1강][초급] [6]
권선중 2005/06/24  5447
60
     [끼적강좌 5] 로그인 구현강좌 [2강][중급] [2]
권선중 2005/06/25  5568
59
       [끼적강좌 5] 로그인 구현강좌 [3강][고급] [3]
권선중 2005/06/26  5352
58
         [re] [끼적강좌 5] 로그인 구현강좌 [4강][다계정 구현] [5]
권선중 2005/06/27  5004
57
   마우스 오른쪽 눌렀을때의 메뉴 뜨게하기(초보용)
이시영 2005/02/02  5144
56
   [쉬운강좌1]환경파일 다루기 [3]
정성우 2005/01/11  5461
55
   영문 윈도우에서의 창조로 만든 프로그램.. [16]
손상진 2005/01/02  5942
54
   [ps.구루 강좌 #12♭]포인터를 왜 씁니까? [2]
ps.이진백 2004/12/31  6308

     [re] [ps.구루 강좌 #12♭]포인터를 왜 씁니까? [1]
지상현 2005/01/01  5622
52
   창조의 한계를 뛰어 넘어서 #1: '문자' 포인터 써먹기 [4]
지상현 2004/11/23  6931
51
   [ps.구루 강좌#11] 서비스팩2에서 프로그램 추가/제거 설정
ps.이진백 2004/10/26  5464
50
   대박로또에 적용된 자동업데이트 알고리즘.. [7]
최재일 2004/09/13  7936
49
   [삐까뻔쩍강좌] 오랜만에 글쓰네.. [10]
박재성[날개달기] 2004/09/07  4983
48
   [보충강좌#10-1] *.Res를 위한 *.Rc [1]
ps.이진백 2004/08/12  6154
47
   [강좌#10] DLL에 HTML 쑤셔넣기 [6]
ps.이진백 2004/08/06  6211
46
   방금생각한 암호화 알고리즘 - -;; [2]
박재성[날개달기] 2004/07/29  5667
45
   [끼적강좌 4] 창조 구현 DB강좌 [1강] [5]
권선중 2004/07/25  5825
LIST ALL   Prev [1][2] 3 [4][5] Next
Copyright 1999-2024 Zeroboard / skin by reedyfox in miniwini style
로그인
지우개 Expert 3.0
제작자 : 천호성 님 [LINK]
로그인
대박로또2005
제작자 : 최재일 님 [LINK]
로그인
1박종훈15292 점
2지상현8809 점
3손상진7388 점
4권선중6060 점
5이진백5174 점
로그인
가입일닉네임
05/31김동률
03/31홍형기
09/01o00pp99oo
12/27이재민
11/20이희철
로그인