線上訂房服務-台灣趴趴狗聯合訂房中心
發文 回覆 瀏覽次數:1805
推到 Plurk!
推到 Facebook!

在function中不能free自已設的變數?

答題得分者是:syntax
大支豬
一般會員


發表:1
回覆:7
積分:1
註冊:2002-08-06

發送簡訊給我
#1 引用回覆 回覆 發表時間:2002-09-09 20:58:43 IP:203.69.xxx.xxx 未訂閱
在function中不能free自已設的變數? [版本一] 在一個form中放入button,memo,combobox 自訂一個function如下,並在button onclick呼叫 function TForm1.GetMemoItems: TStringList; var i : integer ; aTStringList : TStringList ; begin i := 0; aTStringList:= TStringList.Create; aTStringList.Clear; for i := 0 to Memo1.Lines.Count-1 do begin aTStringList.Add(Memo1.Lines[i]); end; Result := aTStringList; // aTStringList.Free; end; procedure TForm1.Button1Click(Sender: TObject); begin ComboBox1.Items := GetMemoItems; end; 版本一如果把註解拿掉,則會出error [版本二] var aTStringList : TStringList ; function TForm1.GetMemoItems: TStringList; var i : integer ; begin i := 0; for i := 0 to Memo1.Lines.Count-1 do begin aTStringList.Add(Memo1.Lines[i]); end; Result := aTStringList; end; procedure TForm1.Button1Click(Sender: TObject); begin aTStringList:= TStringList.Create; aTStringList.Clear; ComboBox1.Items := GetMemoItems; aTStringList.Free; end; 在版本二中,如果把Create和Free寫在Function外則正常 想請問的是在一個function中就算已把Result指給aTStringList, 不能在此function中free掉這個aTStringList變數嗎?
領航天使
站長


發表:12216
回覆:4186
積分:4084
註冊:2001-07-25

發送簡訊給我
#2 引用回覆 回覆 發表時間:2002-09-09 21:10:57 IP:61.219.xxx.xxx 未訂閱
result雖然已經指到aTStringList變數,但那只是指到它的位址指標而已, 並非將整個陣列傳出去,所以您不可以Free掉他,因為外部的呼叫者需要用到它! 不然就將aTStringList當做參數傳入Function中,但也是需要在呼叫之前先Create好! 總之變數總是需要一塊配置的記憶體空間來使用的! ~~~Delphi K.Top討論區站長~~~
------
~~~Delphi K.Top討論區站長~~~
大支豬
一般會員


發表:1
回覆:7
積分:1
註冊:2002-08-06

發送簡訊給我
#3 引用回覆 回覆 發表時間:2002-09-09 21:43:14 IP:203.69.xxx.xxx 未訂閱
引言: result雖然已經指到aTStringList變數,但那只是指到它的位址指標而已, 並非將整個陣列傳出去,所以您不可以Free掉他,因為外部的呼叫者需要用到它! 不然就將aTStringList當做參數傳入Function中,但也是需要在呼叫之前先 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Create好! 總之變數總是需要一塊配置的記憶體空間來使用的! ~~~Delphi K.Top討論區站長~~~
謝謝您的回應,但如果照此說法, 如果執意一定要在此function中create and free掉自已create的變數,要如何做?(plz給個範例)
ccchen
版主


發表:61
回覆:940
積分:1394
註冊:2002-04-15

發送簡訊給我
#4 引用回覆 回覆 發表時間:2002-09-10 08:00:21 IP:61.219.xxx.xxx 未訂閱
兩個版本均錯了, 問題不在  在function中不能free自已設的變數? 而是根本記憶體管理完全錯誤 ComboBox1.Items為一指標指向本身已配置之記憶體 aTStringList:= TStringList.Create; create另一塊Memory,aTstringlist指向此新Create之記憶體. ComboBox1.Items := GetMemoItems; 將combobox1.items之指標指向新配置之記憶體, 故原來自己的記憶體再也沒人管了 其實你的程式看起來只是要將Memo1.lines之內容抄到Combobox1.items Combobox1.items.addstrings(Memo1.lines) 一行就可以了 發表人 - ccchen 於 2002/09/10 08:24:07
領航天使
站長


發表:12216
回覆:4186
積分:4084
註冊:2001-07-25

發送簡訊給我
#5 引用回覆 回覆 發表時間:2002-09-10 08:06:50 IP:61.219.xxx.xxx 未訂閱
引言: 如果執意一定要在此function中create and free掉自已create的變數,要如何做?(plz給個範例)
如果一定要在function中free掉您create的空間,那麼離開function後,就無法使用這一愧空間內的資料了,您不是要將資料傳出來嗎? 可否改用變數傳入的方式? 我寫了一個範例 procedure TForm1.GetMemoItems(aTStrings: TStrings); var i : integer ; begin i := 0; aTStrings.Clear; for i := 0 to Memo1.Lines.Count-1 do begin aTStrings.Add(Memo1.Lines[i]); end; end; procedure TForm1.Button1Click(Sender: TObject); begin GetMemoItems(ComboBox1.Items); end; 您是不是要把TMemo的資料轉入TComboBox? ~~~Delphi K.Top討論區站長~~~
------
~~~Delphi K.Top討論區站長~~~
大支豬
一般會員


發表:1
回覆:7
積分:1
註冊:2002-08-06

發送簡訊給我
#6 引用回覆 回覆 發表時間:2002-09-11 00:17:24 IP:203.69.xxx.xxx 未訂閱
說明:這個例子只是為了如何試TStrings及TStringList(因為memo和ComboBox有TStringList可以玩)只是在試的過程中,發現不能free,因為從以前到現在的觀念,自已create的一定要記得自已free掉,進而產生"在function中不能free自已設的變數?"這個問題例子舉的不好,sorry :Q,不要打偶 衍生問題一:在function中,若自行create任何東西,而其有被"result"參考到的,均不能在這個function中free掉嗎? 衍生問題二:偶的指標(pointer)觀念超爛的,想請教的是如果偶想把二個TStringList型態的東西,從甲方TStringList內容覆製到乙方TStringList,能不能塞指標直接指過去?另外,是否有其它方法(ex:函數)能直接塞?
syntax
尊榮會員


發表:26
回覆:1139
積分:1258
註冊:2002-04-23

發送簡訊給我
#7 引用回覆 回覆 發表時間:2002-09-11 03:33:58 IP:203.204.xxx.xxx 未訂閱
引言: 說明:這個例子只是為了如何試TStrings及TStringList(因為memo和ComboBox有TStringList可以玩)只是在試的過程中,發現不能free,因為從以前到現在的觀念,自已create的一定要記得自已free掉,進而產生"在function中不能free自已設的變數?"這個問題例子舉的不好,sorry :Q,不要打偶 衍生問題一:在function中,若自行create任何東西,而其有被"result"參考到的,均不能在這個function中free掉嗎? 衍生問題二:偶的指標(pointer)觀念超爛的,想請教的是如果偶想把二個TStringList型態的東西,從甲方TStringList內容覆製到乙方TStringList,能不能塞指標直接指過去?另外,是否有其它方法(ex:函數)能直接塞?
1. 問題很奇怪.... Result 是不 *參考* 任何東西的,而是你要指定其值 所以問題本身就有問題 而既然要指定其值,就代表要有東西,即使是nil 所以你的程式設計基礎知識需要加強 2. 可以用 properties Text --> aStringList.Text := bStringList.Text; 你應該好好看看 Delphi 的 Help 如果你有看,就不會問這個問題了 TStringList 說穿了 也不過是一個 String 的封裝而已 簡單的說 TStringList 是一個 String 變數,加上一些額外的處理函式的 Class 而已,而Tstring 則是處理函式中沒有實際的程式碼,只有虛殼而已, Delphi Help 中說的很間單也很明白,建議你花點心思看看
G01
高階會員


發表:249
回覆:379
積分:215
註冊:2002-05-21

發送簡訊給我
#8 引用回覆 回覆 發表時間:2002-09-16 08:34:02 IP:210.61.xxx.xxx 未訂閱
[/quote]  前面省略......    衍生問題一:在function中,若自行create任何東西,而其有被"result"參考到的,均不能在這個function中free掉嗎?    Anser : 問題並不在於"能不能Free掉",而是在Free掉之前函式是否已經將該物         件的值傳遞出去了. 因為我們無法確定(控制)函式何時傳出Result的         值,所以當你Free掉該物件之後;而Result要取值時,當然是找不到資料         !!         如果大家還記得的話,Delphi不是還由另一規定是:         "物件的Property 不可以帶入宣告為 'Var' 的函式參數中",其實這是         相同的道理!!    [/quote] 
系統時間:2024-04-20 13:33:18
聯絡我們 | Delphi K.Top討論版
本站聲明
1. 本論壇為無營利行為之開放平台,所有文章都是由網友自行張貼,如牽涉到法律糾紛一切與本站無關。
2. 假如網友發表之內容涉及侵權,而損及您的利益,請立即通知版主刪除。
3. 請勿批評中華民國元首及政府或批評各政黨,是藍是綠本站無權干涉,但這裡不是政治性論壇!