델파이에서 사용자가 생성하는 모든 클래스는 TObject클래스를 상속받는다고 알고 있습니다. (TMyClass = class 라고 선언해도 사실은 TMyClass = class(TObject)가 되는 거죠) 그런데 제가 지금 만들고 있는 프로그램에서 데이타를 동적으로 많이(때로는 아주 많이) 생성해서 TList에 Add해야 하는 상황이 생깁니다.
클래스 안에는 integer변수 5개와 string 변수 한개가 있고 생성자를 이용해서 변수들을 초기화 합니다. integer변수는 한개에 32bit(4byte)를 차지하고 string 변수는 한 글자당 한 바이트를 차지한다고 알고 있습니다.
여기서 string 변수는 16글자 이상이 되는 경우가 거의 없습니다. 대부분 1글자...
그렇다면 클래스에 들어간 변수들을 크기를 따져볼때 4byte X 5 + 최대 16byte = 36byte를 넘지 않습니다.
그런데 이런 변수들을 많이 생성하게 되니까 제 프로그램이 메모리를 수십MByte에서 심지어는 100MByte를 넘게 차지하는 일이 생깁니다. 제 생각에는 TObject클래스를 상속하기 때문에 제가 추가하지는 않았지만 클래스가 어쩔수 없이 차지하게 되는 메모리가 크기 때문에 그런 것 같습니다.
1. 메모리를 저렇게 많이 차지하게 되는 이유가 '기본적으로 TObject를 생성하게 될때 생기는 변수들'때문이 맞나요?
2. 그렇다면 클래스를 사용하지 않고 변수를 동적생성해서 TList에 Add시키는 방법이 있을까요?? record형을 정의해서 포인터를 사용하면 될 것 같은데...제가 경험이 부족해서 잘 모르겠습니다. ㅠㅠ
델파이 고수분들께서 도와주신다면 정말 감사하겠습니다. 좋은 주말 되세요~^
고수는 결코 아닙니다만....
TList 의 경우 Add Parameter로 포인터를 넘기는 걸로 알고 있습니다. Add 할 때마다 4byte씩
차지 합니다. 그리고 원래 Parameter로 포인터를 넘기기 때문에 당연히 record형을 정의 해서 포인터를
넘겨 줄수 있습니다. 그리고 개인적으로 메모리를 100MB씩 차지한다고 그리 걱정할 필요는 없을 듯
합니다. 메모리가 새지 않는 이상 오히려 메모리를 충분히 활용하여 퍼포먼스를 높이거나 다른 이익
을 얻는다면 괜찮지 않나 싶습니다. 아래 소스는 허접하니 참고만 하시구염.. 다른 고수님들이 봐주실
듯 합니다.
<!--CodeS-->
procedure TForm1.Button1Click(Sender: TObject);
type
TTestRecord = record
Str : array [0..99] of char;
Int1 : integer;
Int2 : integer;
end;
pTestRecord = ^TTestRecord;
var List : TList;
TestRecordArray : array [0..9] of TTestRecord;
i : integer;
Str : string;
begin
List := TList.Create;
for i := 0 to 9 do
begin
Str := 'Test' + IntToStr(i);
StrPCopy(@TestRecordArray[i].Str, Str);
TEstRecordArray[i].Int1 := i * 2;
TestRecordArray[i].Int2 := i * 20;
end;
for i := 0 to 9 do
begin
List.Add(@TestRecordArray[i]);
end;
for i := 0 to 9 do
begin
Memo1.Lines.Add( TTestRecord(List.Items[i]^).Str );
end;
List.Free;
List := nil;
end;
<!--CodeE-->