빌더(TWx) 님이 쓰신 글 :
: 100jk 님이 쓰신 글 :
: : 아래와 같은 소스가 있습니다.
: :
: : var
: : b, b2: Tbitmap;
: : begin
: : b := tbitmap.create;
: : b2 := b;
: : b.free; //비트맵해제
: : //{이곳에 판단식을 넣고싶습니다.}
: : b2.free; //당연히 에러
: :
: : b2를 해제하기 전에 b2주소에 있는 비트맵(혹은 다른 클래스)이 이미 해제되어있는 상태인지
: :
: : 판단할 수 있는 방법이 있나요?
:
:
:
: 답변:
:
:
: 파일 생성과 삭제를 반복하다 보면 디스크 Fragment(단편화)가 발생하는 것과 마찬가지로
: 메모리도 할당과 삭제를 반복하게 되면 Fragment가 발생하게 되어...
: Free 메모리 총합은 여유가 있어도, 메모리 할당에 실패하는 경우가 발생하게 됍니다.
: 1.5GB 프리 상태인데 1GB 할당에 실패하는 경우 등.
:
:
: 메모리 메니지먼트 코드를 구현할 때...
:
: 1.
: 단편화를 최대한 줄이는 쪽으로 메모리를 효율적으로 사용할 수 있도록 하기위해 알고리즘 구현에
: 공을 들여서 구현하는 방법이 있고...
:
: 2.
: 메모리를 Small, Medium, Large로 Heap 블럭으로 나누어서 사용하되, Chaind Block 리스트로 Small Block 을
: 별도로 관리하는 간단한 방법으로 구현할 수도 있는데...
:
:
: 델파이 메모리 매니지먼트 내부코드는 2.번의 단순한 방법을 이용해서 구현되어 있습니다.
:
:
: 델파이 언어는 exception 발생 여부와 상관없이 메모리 같은 리소스를 안전하게 해제하기 위해
: 반드시 try... finally 블럭을 사용해야 하는 반면에, C++은 exception 발생 여부와 상관없이 RAII 패턴을 이용해서
: 리소스를 안전하게 해제할 수 있어서... 퍼포먼스 면에서는 C++이 훨씬 유리하지요.
:
:
:
: 본론으로 돌아와서...
:
: 할당되어 있던 메모리가 해제 됐는지 아닌지는 델파이 메모리 매니지먼트 내부구조를 이해하고 있으면
: 간단하게 알아 낼 수 있습니다.
:
: memory management 내부구조는 델파이 버전에 따라 다를 수 있어서...
: 설치되어 있는 rad 10.3.1 기준으로 설명합니다.
:
:
: function IsFreed(var obj ): Boolean;
: begin
: Result := PULONG_PTR(PByte(obj) - sizeof(ULONG_PTR))^ and 1 <> 0;
: end;
:
: procedure TForm1.Button1Click(Sender: TObject);
: var b1, b2: TBitmap;
: begin
: b1 := TBitmap.Create;
: b2 := b1;
:
: b1.Free;
: if IsFreed(b2) then
: Memo1.Lines.Add('b2 freed.');
: end;
:
:
:
:
: 위와 같이 처리하면 할당되어 있던 메모리의 해제여부를 쉽게 알아 낼 수 있습니다만...
:
: std::shared_ptr 이용해서 C++로 코딩하면 공유 메모리 관리에 신경 쓸 일이 없지요.
:
예전부터 정말 궁금했던 내용인데 답변 정말 감사드립니다.
윈도우에서 정상작동 하는걸 확인했습니다.
혹시 FMX에서도 해당내용이 구현이 가능할까요?
PULONG_PTR, ULONG_PTR 등이 winapi.windows에 정의 되어있어 다른 플랫폼에서는
해당 기능이 구현이 컴파일이 안되네요.