2016-12-07 12 views
2

은 내가 VCL이 코드는 응용 프로그램 양식이 있습니다TBitmap 변수를 해제 할 때 액세스 위반 - 해제 후 비트 맵 변수가 여전히 할당 되었습니까?

implementation 

{$R *.dfm} 

var 
    MyBitmap: TBitmap; 

procedure TFormMain.FormCreate(Sender: TObject); 
begin 
    MyBitmap := TBitmap.Create; 
end; 

procedure TFormMain.FormDestroy(Sender: TObject); 
begin 
    if Assigned(MyBitmap) then 
    MyBitmap.Free; 
end; 

procedure TFormMain.Button1Click(Sender: TObject); 
begin 
    if Assigned(MyBitmap) then 
    MyBitmap.Free; 
end; 

내가 버튼을 내가 버튼의 클릭 핸들러에서 MyBitmap.Free;에서 액세스 위반을 얻을 두 번째 시간을 클릭합니다. 그러나 MyBitmap은 첫 번째 버튼 클릭 이후에 더 이상 할당되어서는 안됩니다. 그렇다면 왜 if Assigned(MyBitmap) then 상태가 첫 번째 버튼 클릭에서 분명히 작동했을 때 두 번째 버튼 클릭에서 작동하지 않는 이유는 무엇입니까? 포인터가 Nil을 할

델파이 10.1 베를린 업데이트 2

+1

개체 참조를 해제해도 nil과 같지 않은지 확인 된 검사는 아무 것도하지 않습니다. 그러므로 당신은 두 배의 자유를 시도하고 있습니다. –

+0

'System.SysUtils.FreeAndNil (MyBitmap)'이 AV없이 작업을하는 것으로 보입니다. – user1580348

+0

결론적으로 우리는 OBJECT가 FREE로 릴리즈 될 수 있고 OBJECT VARIABLE이 NIL로 설정 될 수 있다는 것을 배웠다. 이 올바른지? – user1580348

답변

6

Assigned 기능은 확인합니다. 기존 개체를 가리키는 지 여부를 확인하지 않습니다. Assigned 기능을 원하는대로 작동 시키려면 해제 한 후 Nil으로 설정해야합니다. FreeAndNil은 두 명령을 모두 수행합니다.

+0

'Free'를 사용하는시기와 객체 변수를 해제 할 때'FreeAndNil'을 사용하는시기에 대한 공통 규칙이 있습니까? – user1580348

+0

@user - 오브젝트가 여러 위치에서 해제 될 가능성이있는 경우 FreeAndNil이 유용 할 수 있습니다. 하지만 그렇게 흔한 것은 아닙니다. –

+2

이것은 의견을 기반으로합니다. IMHO 참조 된 개체가 해제 된 후에 변수에 액세스 할 수있게되면 개체 참조를 해제 한 후 개체 참조를 'Nil'로 설정해야합니다. 그래서'Free' 후에 일어날 일이 없을 때 메서드에서 지역 변수를'Nil' 할 필요는 없습니다. 어느 누구도이 변수에 액세스 할 수 없습니다. 클래스의 멤버 변수에 저장되고 소멸자에서 해제 된 객체 참조에 대해서도 동일하게 적용됩니다. 그러나 객체의 수명 동안 '자유롭게'할 때 (예 : 버튼 클릭 내에서 양식의 멤버를 비우는 등) 해당 객체를 추가로 삭제하면 안됩니다. – Wosi