在类中的动态二维数组的问题! ( 积分: 100 )

  • 主题发起人 主题发起人 拉飞
  • 开始时间 开始时间

拉飞

Unregistered / Unconfirmed
GUEST, unregistred user!
TGA=class(Tobject)
private
aa:array of array of integer;//定义的二维动态数组
public
procdure init();//初始化
procedure ....
....
end;
{TGA}
//
procedure TGA.init();
begin
//分配空间
setlength(aa,2);//出错,当aa为一维动态时,正常
//为什么不能为动态二维的

end;
 
如果aa在init中声明,则可以
procedure TGA.init();
var
aa:array of array of integer;//二维动态数组
begin
//分配空间
setlength(aa,2);//正常
end;
为什么aa作为类成员的时候不能分配,所谓函数的私有变量的时候可以。
是类的问题,还是setlength的问题?
那位老大能够解释一下,谢谢了!
 
既然是二维的,
分配空间就要分给它行和列
Setlength(aa,2,2);
 
哎,看来ploe对二维数组也是知之甚少。
二维的数组也可以一维一维的分配,
setlength(aa,2);
setlength(aa[1],3);
我做过几个验证,如果动态的二维有一维固定的话,也是可以的。
比如:
bb=record
a1:integer;
a2:array[0..2] of integer;
end;
TGA=class
private
aa:array of bb;
............
这时候aa作为类的数据成员,也是可以正常分配空间的。
如果反过来:
bb=record
a1:integer;
a2:array of integer;
end;
TGA=class
private
aa:array[0..2] of bb;
..............
在setlength(aa[1],2)的时候出错。
 
难道这个问题很简单吗?高手们都不屑一顾?
如果分少我还可以再加!我还有1000多分那。
 
能不能有劳menxin或cAkk 斑竹大人在百忙之中,抽出一丁点时间作答一下。
在此万分感谢了!!!!!
 
怎么还没有人回答我的问题?
如果能得到满意答复,再开帖送200分
 
并且我还发现一个奇怪的现象:
如果这个类不是我自己定义的,而是Tform类,动态二维数组可以正常分配空间。
我对类了解的不是很多,望高手能够指点指点。
 
类中的数据成员和临时变量在内存中分配的是不一样的,你的类必须先创建一个对象才能给动态数组分配空间。
TGA=class(Tobject)
private
aa:array of array of integer;//定义的二维动态数组
public
procdure init();//初始化
procedure ....
....
end;
{TGA}
//
procedure TGA.init();
begin
//分配空间
setlength(aa,2);//出错,当aa为一维动态时,正常
//为什么不能为动态二维的

end;

tmpGA := TGA.Create;
tmpGA.Init;
 
nicai_wgl说的有道理,这是我的疏忽,我做这个GA的类时,自己构造了一个函数create,想初始化的内容放在其中,分配空间就在这个构造函数中,所以举例的时候就忘记创建出对象了。我还没有试,这种方法应该是可行的吧。这也能解释为什么Tform类可以,在窗体载入的时候,自动加载其create过程。
不过我还有一点搞不清楚,为什么对象在创造以前可以给一维动态数组分配空间,而二维动态数组空间就不可以?
能否再赐教?
 
这个问题和类的性质没有任何关系。

正确的方法是先显式的定义类型:
My2DArray = array of array of integer;

然后明确指出变量的类型:
faa : My2DArray;

最后你就可以随便用这个变量了;
SetLength(faa,2);这是设定了faa的第一维;
它的第2维要另外设定SetLength(faa[0],3);
 
To: nicai_wgl
可能你提供的方法你自己也没有验证吧?
今天我验证了一下,在[red]tmpGA := TGA.Create;[/red]处出错!!!
To :沙隆巴斯的主人
这种显式声明的方法我一开始就用了,出错的特征标识没有什么区别。
如果不信的话,你自己简单验证一下就行了。当然要自己定义的类,比如:
myclass=class(Tobject)

另:我在Tform这个类中用这个动态的二维数组就没有任何问题,,所以我觉得还是跟类
有很大的关系。我只试了Tobject和Tform这两个类,DelphiVCL框架下的其他类还
没有试。
 
望大侠们不吝赐教,不管结果如何,我定当再开帖送200分。
 
无忧站网络——专业提供虚拟主机、域名注册、网页制作、LOGO制作、网站推广等服务。
更多空间详情请登陆 http://www.51zhan.com
 
1、在类中或记录中的长字符串、Variant、对象需要用 Initialize 过程初始化,不过在你的程序中用不到:
procedure TGA.init;
begin
Initialize(aa);
SetLength(aa, 2);
end;
2、你在1楼的程序没有问题,我已经试过了,不要大惊小怪;
3、你在4楼的程序肯定会出问题:
bb = record
a1:integer;
a2:array of integer;
end;
TGA = class
private
aa: array[0..2] of bb;
在setlength(aa[1], 2)的时候出错
aa[1] 是一个 bb 类型的记录,你给一个记录设置长度不出错才怪!
4、你的程序出错可能是别的原因,你最好把 Create 的代码都贴出来。
 
应该是对像没创建而造成的非法访问

但在 TGA.init中对局部变量数组设置长度不会出错呢?原因是,不管对像创没创建,通过对像名都能够访问到init方法(因为对像名的类型是确定了的),即然能访问方法,则会为该方法的局部变量分配空间,所以对局部变量的数组访问不会出错,但是类的变量(不是方法的局部变量)没有创建,没有分配空间,所以访部类的变量时出错了
 
最近回到家里,上网非常不方便,没有及时回复,不好意思。
 
TO vvyang:
首先万分感谢你的回答,根据你提出的几点我作了检验:
我的系统是xp,delphi7:
1)我在1楼的程序如下:
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls;
type
//TGA class
TGA=class(Tobject)
private
a1:array of array of integer;
public
procedure Init();
end;

TForm1 = class(TForm)
Button1: TButton;
procedure Button1Click(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;

var
Form1: TForm1;

implementation
var bb:TGA;

{$R *.dfm}

{ TGA }

procedure TGA.Init;

begin
setlength(a1,5);
setlength(a1,0);
end;

procedure TForm1.Button1Click(Sender: TObject);

begin
bb.Init ;
end;

end.

这个程序在setlength的时候出错。
 
2)4楼的程序的确出现明显的错误,改正后如下:
bb = record
a1:integer;
a2:array of integer;
end;
TGA = class
private
aa: array[0..2] of bb;
在setlength(aa[0].a2, 2)的时候出错!
 
3) 现在家里,程序代码都没带回来,等过完春节再贴出来,到时候开帖给你们送分!

TO StealDream:
在创建类的时候,调用create出错。(这个create不是我自己的构造函数,是delphi自己的)。
 

Similar threads

S
回复
0
查看
1K
SUNSTONE的Delphi笔记
S
S
回复
0
查看
900
SUNSTONE的Delphi笔记
S
S
回复
0
查看
3K
SUNSTONE的Delphi笔记
S
S
回复
0
查看
2K
SUNSTONE的Delphi笔记
S
后退
顶部