이벤트에서 객체를 delete하면 안되는 이유는?
아래 코드를 보면
님께서 Calender의 OnClick이벤트에서 Calenter객체를 delete하였습니다.
OnClick에 연결한 calendarEvent 라는 메소드는 새로 생성한 TMonthCalendar 클래스에서 호출되는것입니다.
이벤트가 호출된후에 Calender 객체 멤버에 대한 접근이 있는데.. 객체를 지워버리면.. access violation이 날수 밖에 없죠
vcl컴포넌트의 자동 소멸은?
vcl객체의 자동 소멸은 .. 크게 2가지로 분류됩니다.
대표적은 것은 객체를 생성할때 넘겨준 첫번째 인지 Owner 라는 놈에 달려있습니다.
Owner가 free될때 자신을 owner로 가지고 있는 모든 Component를 free시킵니다.
아래코드에서는 calender객체를 생성하면서 Owner로 this즉 Form1을 넘겨줬으므로
Form1이 free될때 calender도 자동으로 free되는것입니다.
두번째는 Control의 경우 parent가 free될때 자동 free됩니다.
아래코드에선 calender의 parent로 Form1을 주었기 때문에 Form1이 free될때 자동으로 free되는데요
만약 calender를 Panel위에 올렸으면 Panel이 free될때 자동으로 calender도 free됩니다.
제생각은..
어쨌든 제 생각은 ..
위와같이 Bitbtn이 click될때마다 Calender를 동적생성하는 방법보다
하나 미리 생성해놓구...(디자인타임에 생성해도 되구요)
필요없으면 visible=false해두시면 될것 같습니다.
객체의 free는 프로그램 종료될때 자동으로 되게 하구요
그럼..
동철이 님이 쓰신 글 :
: 폼 하나에다 버튼하나가 있고 그 버튼을 클릭하면 달력컴포넌트(TMonthCalendar)가 뜨게 합니다. 거기서 날짜정보를 받고 이 컴포넌트를 닫으려고 다음과 같이 해주니깐 access violation error가 납니다.
:
:
: void __fastcall TForm1::BitBtn1Click(TObject *Sender)
: {
: calendar = new TMonthCalendar(this);
: calendar->Parent = Form1;
: calendar->Left = 68;
: calendar->Top = 240;
: calendar->Width = 60;
: calendar->Height = 70;
:
: calendar->OnClick = calendarEvent;
: }
: //---------------------------------------------------------------------------
:
: void __fastcall TForm1::calendarEvent(TObject *Sender)
: {
: TDateTime pdate;
: AnsiString str;
: pdate = calendar->Date;
: str = pdate.DateString();
: ShowMessage(str.SubString(1,4));
: ShowMessage(str.SubString(6,2));
: ShowMessage(str.SubString(9,2));
: delete calendar; // <-- 이 부분 실행 후 에러 발생.
: }
:
: 저도 new 한 함수와 delete한 함수가 서로 다른데서 찜찜한 감이 오긴 왔습니다만...
:
: 보통 컴포넌트를 동적으로 불러내고 메모리에서 삭제하려면 이런 식으로 하면 안되는 건가요?
:
: 아예 그냥 프로그램에서 알아서 힙 메모리에서 해제하도록 delete 안하는게 나을까요?