全國最多中醫師線上諮詢網站-台灣中醫網
發文 回覆 瀏覽次數:1607
推到 Plurk!
推到 Facebook!

FreeAndNil這個程序是不是有些多餘?

答題得分者是:change.jian
0908
一般會員


發表:10
回覆:4
積分:2
註冊:2002-12-31

發送簡訊給我
#1 引用回覆 回覆 發表時間:2004-05-11 13:50:37 IP:218.165.xxx.xxx 未訂閱
我實在搞不懂如果我要釋放一個物件直接將他free掉不就行了!如果再不放心那就再將設為nil!那為什麼會有一個FreeAndNil程序出來!難道他的執行速度會比較快麼?還是他有一些特殊的用法!能不能各位指點一下! suen
------
孫鍾銳
Fishman
尊榮會員


發表:120
回覆:1949
積分:2163
註冊:2006-10-28

發送簡訊給我
#2 引用回覆 回覆 發表時間:2004-05-11 14:34:19 IP:210.65.xxx.xxx 未訂閱
Hi 0908,    請看各位大大們精闢的見解: http://delphi.ktop.com.tw/topic.php?topic_id=48788 很慚愧,我到現在還是一知半解 ---------------------------------- 小弟才疏學淺,若有謬誤尚請不吝指教 ----------------------------------
------
Fishman
change.jian
版主


發表:29
回覆:620
積分:439
註冊:2003-06-02

發送簡訊給我
#3 引用回覆 回覆 發表時間:2004-05-11 17:13:24 IP:61.222.xxx.xxx 未訂閱
0908,您好:   以下列的程式碼來說
 
procedure TForm1.Button1Click(Sender: TObject);
var
  aObj:TComponent;
begin
  aObj:=TComponent.Create(Self);
  try
    ....
  finally
    aObj.free;
    aObj:=nil;
  end;
end;
當您宣告了aObj:TComponent,程式已做了兩件事: 1.向OS要了一個可以容納TComponent物件大小的記憶體區塊 2.把aObj指向"要到的記憶體"的起始位置. 所以,即使程式沒有執行到aObj:=TComponent.Create,但以Assigned去檢查aObj的話,會發現回傳的是True值. 同理,即使執行了aObj.Free,再以Assigned函數檢查aObj,仍然會回傳True值.只有當你把aObj設為nil時,Assigned才會回傳False. 您可以把aObj想像成地址.把TComponent想像成一棟建築物.宣告 Obj:TComponent 時,其實只是告訴戶政事務所(假設戶政事務所管地址)你要在aObj這個地址建一棟建築物.至於你什麼時候建,戶政事務所並不理會.這時,如果你沒有把建築物建立起來,就開始向別人公開你的地址的話,就會發生郵差到了該地址送信時,發現沒有建築物,也沒有人收信.這時,程式就會給你一個"Access violation at address XXXXXXXX in module...."的錯誤訊息.同樣的,若干年後建築物不需要用到了,你把建築物打掉,其實只相當於呼叫物件的free方法,但戶政事務所仍然認定那個地址有建築物.直到aObj:=nil時,才是向戶政事務所通知我的房子打掉了,不存在了. 當然,如果你沒有把房子打掉,就直接跟戶政事務所說那個地址沒有用了.那麼,你的建築物將因為沒有地址,再也沒有人可以找到他的所在地了,也就是記憶體流失了.所以最省事的做法,就是建築物打掉時,也要跟戶政事務所說這個地址沒有用了,要這樣做,FreeAndNil是個不錯的方法. 故事說完了,好不好聽啊
jest0024
高階會員


發表:11
回覆:310
積分:224
註冊:2002-11-24

發送簡訊給我
#4 引用回覆 回覆 發表時間:2004-05-11 17:30:22 IP:203.67.xxx.xxx 未訂閱
//以下函數參考Delphi源碼
procedure FreeAndNil(var Obj);
var
  Temp: TObject;
begin
  Temp := TObject(Obj);
  Pointer(Obj) := nil;
  Temp.Free;
end;    同於
begin
  Obj.Free;
  Obj:=nil;
end;    範例一
procedure Test
var
  Obj:TObject;
begin
  Obj:=TObject.Create;
  //註Obj是指向系統建立OBJECT的一個指標
  Obj.Free;
  Obj:=nil; {在私用程序上,程序執行完便釋放了,其他的程序未參考OBJ所
             以這行可以省掉!!}
end;    範例二
var
  Obj:TObject;    procedure Test;
begin
  Obj:=TObject.Create; 
  //註Obj是指向系統建立OBJECT的一個指標
  Obj.Free;
  Obj:=nil; {Obj是屬於公用的指標,可能別的程序會參考到這記憶体,如
             果未指向nil,則會造成程式發生錯誤,所這行不可以省}
end;
學而時習之不亦樂乎!
hagar
版主


發表:143
回覆:4056
積分:4445
註冊:2002-04-14

發送簡訊給我
#5 引用回覆 回覆 發表時間:2004-05-11 17:34:05 IP:202.39.xxx.xxx 未訂閱
解釋得真棒! 小弟也懂了! 
shaofu
高階會員


發表:5
回覆:136
積分:103
註冊:2003-01-07

發送簡訊給我
#6 引用回覆 回覆 發表時間:2004-05-11 19:26:54 IP:210.243.xxx.xxx 未訂閱
change.jian 兄講解的方式真的很好, 不過有些地方有錯, 幫忙補正一下  < class="code"> procedure foo: var aObj: TComponent; begin aObj:=TComponent.Create(Self); end; 首先, Delphi 的物件皆是以指標實作, aObj 實際上就是一個指標, 把 aObj 當成指標來想, 後面的解說就很容易了.. aObj: TComponent; 這行說明 aObj 是個 TComponent 的物件(指標), 但這邊有一個重點 "complier 不會幫 local variable 做初使化", 也就是 aObj 的值在剛開始並沒有任何意義, 可以想為只是個亂數值... (PS: 反之 global variable 則預設會初使化為 0) TComponent.Create(Self); 向OS要了一個可以容納TComponent物件大小的記憶體區塊, 加上物件的初使化 aObj:=TComponent.Create(Self); 把aObj指向"要到的記憶體"的起始位置. (至此, aObj 的值才有意義) 至於之後的 address 與 value 的關係, change.jian 兄講的就很清楚了, 好比喻 發表人 -
Miles
尊榮會員


發表:27
回覆:662
積分:622
註冊:2002-07-12

發送簡訊給我
#7 引用回覆 回覆 發表時間:2004-05-11 20:07:04 IP:218.160.xxx.xxx 未訂閱
Hi 插個花: Delphi有很多函數, 都是由Borland幫我們實作後方便讓我們使用, 例如一堆DateTime的相關function procedure, FreeAndNil也是同樣的道理, 若我們使用時知道他的原理便可手動去Key程式碼, 效率也許會更快, 這個函數也許是有點多餘, 但竟然Borland已經又幫我們放上去也許是有其他方面的需求. 我不是高手, 高手是正在銀幕前微笑的人.
------


我不是高手, 高手是正在銀幕前微笑的人.
OsX
版主


發表:6
回覆:151
積分:111
註冊:2003-05-03

發送簡訊給我
#8 引用回覆 回覆 發表時間:2004-05-11 21:33:18 IP:211.76.xxx.xxx 未訂閱
引言: Hi 插個花: Delphi有很多函數, 都是由Borland幫我們實作後方便讓我們使用, 例如一堆DateTime的相關function procedure, FreeAndNil也是同樣的道理, 若我們使用時知道他的原理便可手動去Key程式碼, 效率也許會更快, 這個函數也許是有點多餘, 但竟然Borland已經又幫我們放上去也許是有其他方面的需求. 我不是高手, 高手是正在銀幕前微笑的人.
我也來插花, 之前在 Borland News Group 看到的, FreeAndNil() 這個函式由來, 並不是有其它特殊理由或原因才加進去的, 是因為有人向 Borland 反應 寫
 
   Obj.Free;
   Obj := nil;
看起來很笨(原文好像是Stpuid Code) 於是向 Borland 反應, Borland 便把這個函式從 Delphi6 開始加進去, 滿足 這些人的要求.
Fishman
尊榮會員


發表:120
回覆:1949
積分:2163
註冊:2006-10-28

發送簡訊給我
#9 引用回覆 回覆 發表時間:2004-05-12 08:36:46 IP:210.65.xxx.xxx 未訂閱
各位大大,    真是精采,佩服!佩服! 小弟總算是懂啦,感謝 發表人 -
------
Fishman
0908
一般會員


發表:10
回覆:4
積分:2
註冊:2002-12-31

發送簡訊給我
#10 引用回覆 回覆 發表時間:2004-05-12 14:18:28 IP:218.165.xxx.xxx 未訂閱
謝謝各位的指點!只有在這裡我才真正感到溫暖和快樂!因為在台灣學習Delphi真是覺得即孤單又寂寞! suen
------
孫鍾銳
hahalin
版主


發表:295
回覆:1698
積分:823
註冊:2002-04-14

發送簡訊給我
#11 引用回覆 回覆 發表時間:2004-05-12 15:44:05 IP:210.243.xxx.xxx 未訂閱
change.jian 大大說得好啊!!! 佩服佩服
系統時間:2024-05-08 21:45:18
聯絡我們 | Delphi K.Top討論版
本站聲明
1. 本論壇為無營利行為之開放平台,所有文章都是由網友自行張貼,如牽涉到法律糾紛一切與本站無關。
2. 假如網友發表之內容涉及侵權,而損及您的利益,請立即通知版主刪除。
3. 請勿批評中華民國元首及政府或批評各政黨,是藍是綠本站無權干涉,但這裡不是政治性論壇!