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

請教ClientDataSet記憶體問題

答題得分者是:leveon
judas81719
一般會員


發表:3
回覆:5
積分:1
註冊:2016-05-31

發送簡訊給我
#1 引用回覆 回覆 發表時間:2017-01-20 11:35:48 IP:60.251.xxx.xxx 未訂閱
請教各位先進
以下程式片段在ClientDataSet2.Active := True; 的部分會顯示Insufficient Memory for This Operation的錯誤
目前了解是記憶體不足所導致的,而其他資料量較小的不會有這問題
想請問是否有解決方法或是替代方案
[code delphi]
try
ClientDataSet2.Active := False;
SQLQuery1.SQL.CommaText := 'SELECT * FROM ' LabelTable.Caption;
SQLQuery1.ExecSQL;
finally
ClientDataSet2.Active := True; //Insufficient Memory for This Operation
end;
[/code]
GrandRURU
站務副站長


發表:240
回覆:1680
積分:1874
註冊:2005-06-21

發送簡訊給我
#2 引用回覆 回覆 發表時間:2017-01-20 18:09:32 IP:42.73.xxx.xxx 未訂閱
請問資料量具體是多大呢?
judas81719
一般會員


發表:3
回覆:5
積分:1
註冊:2016-05-31

發送簡訊給我
#3 引用回覆 回覆 發表時間:2017-01-20 18:33:40 IP:60.251.xxx.xxx 未訂閱
約1300000筆 
而另一個900000左右沒有這問題
想在不變動硬體的情況下改到能夠運作
Jasonwong
版主


發表:49
回覆:931
積分:581
註冊:2006-10-27

發送簡訊給我
#4 引用回覆 回覆 發表時間:2017-01-21 13:19:05 IP:125.227.xxx.xxx 未訂閱
雖然不清楚你一次讀取130萬筆的用途是什麼,不過我能想到的大概以下這幾招

1.如果你的DELPHI有支援 x64,那就編譯成 x64 版
2.只載入KEY的欄位,然後再去下SQL WHERE KEY 方式載入另一個 cds,使用 AppendData 方式,舊有資料不用刪除繼續使用
------
聰明的人,喜歡猜心;雖然每次都猜對了,卻失去了自己的心
傻氣的人,喜歡給心;雖然每次都被笑了,卻得到了別人的心
judas81719
一般會員


發表:3
回覆:5
積分:1
註冊:2016-05-31

發送簡訊給我
#5 引用回覆 回覆 發表時間:2017-01-23 16:06:12 IP:60.251.xxx.xxx 未訂閱
會要一次讀取這麼多檔案的原因是因為這隻程式是先將SQL的資料讀取到本機
然後跑迴圈比對要新增的資料要INSERT還是UPDATE

GrandRURU
站務副站長


發表:240
回覆:1680
積分:1874
註冊:2005-06-21

發送簡訊給我
#6 引用回覆 回覆 發表時間:2017-01-23 17:38:34 IP:59.120.xxx.xxx 未訂閱
我想我會先在 Server 查詢是否存在,之後再進行新增或更新處理
像是
process IsExitsRecord(AField: TFields);
begin
SQLQuery1.SQL.Text := 'SELECT count(*) FROM TABLE_X WHERE F1=:F1 AND F2=:F2';
SQLQuery1.Params[0].Value := AField[0].Value;
SQLQuery1.Params[1].Value := AField[1].Value;
SQLQuery1.Open;
Result := SQLQuery1.Field[0].AsInteger > 0;
end;

while not CDS.Eof do
begin
if IsExitsRecord(CDS.Fields: TFields) then
EditProc
else
InsertProc;
CDS.Next;
end

不然就只能像 Jason 版主說的那樣,編譯成 64 位元版本,也一樣可以達到您的需求

===================引 用 judas81719 文 章=================== 會要一次讀取這麼多檔案的原因是因為這隻程式是先將SQL的資料讀取到本機
然後跑迴圈比對要新增的資料要INSERT還是UPDATE

leveon
資深會員


發表:30
回覆:389
積分:303
註冊:2012-02-12

發送簡訊給我
#7 引用回覆 回覆 發表時間:2017-01-24 16:42:09 IP:1.169.xxx.xxx 未訂閱
不要用ClientDataSet浪費記憶體 拿掉clientdataset
直接用TSQLQuery 滾一圈 單向cursor 只能往前 不能往後

抄一下樓上的Code 改一下

SQLQuery1.SQL.Text := 'SELECT * FROM TABLE_X ;
SQLQuery1.Open;
SQLQuery1.first;

while not SQLQuery1.Eof do
begin
if (SQLQuery1.fieldbyname('XXX').asinteger = 1) then
EditProc
else
InsertProc;
SQLQuery1.Next;
end;

===================引 用 judas81719 文 章===================
會要一次讀取這麼多檔案的原因是因為這隻程式是先將SQL的資料讀取到本機

然後跑迴圈比對要新增的資料要INSERT還是UPDATE
編輯記錄
leveon 重新編輯於 2017-01-24 16:47:18, 註解 無‧
leveon 重新編輯於 2017-01-24 16:47:51, 註解 無‧
leveon 重新編輯於 2017-01-24 16:48:08, 註解 無‧
系統時間:2024-11-23 18:08:56
聯絡我們 | Delphi K.Top討論版
本站聲明
1. 本論壇為無營利行為之開放平台,所有文章都是由網友自行張貼,如牽涉到法律糾紛一切與本站無關。
2. 假如網友發表之內容涉及侵權,而損及您的利益,請立即通知版主刪除。
3. 請勿批評中華民國元首及政府或批評各政黨,是藍是綠本站無權干涉,但這裡不是政治性論壇!