说三道四技术文摘-感悟人生的经典句子
说三道四 > 文档快照

关于传递结构中的指针指向的结构的动态数组问题。

编辑:说三道四文库 发布时间:2018-06-22 12:03
HTML文档下载 WORD文档下载 PDF文档下载

Type 
  TResponse = record
    Return : boolean;
    Command : PChar;
    Buffer : pointer;
  end;
  TrtArr = record
    size : integer;
    arr : array of integer;
  end;

function getData() : pointer;
var p : ^TResponse;
    rt : TResponse;
    rtArr : TrtArr;
begin
    rt.Return:=0;
    rt.Command:=nil;
    rt.Buffer:=nil;
    rt.Size:=0;
    rt.Reserve:=0;

    p:=AllocMem(SizeOf(TResponse));
    result:=p;

    .......... //这里的一些过程对rtArr中的size和动态数组进行了赋值。
    //*********将赋值后的rtArr拷贝到rt.Buffer***************
    rt.Buffer := AllocMem(SizeOf(rtArr));
    move(rtArr, rt.Buffer^, SizeOf(rtArr));
    rt.Size := SizeOf(rtArr);  
    //***********************************************
    rt.Return := true;
    rt.Command := 'SUCCEED';
    move(rt, p^, SizeOf(rt)); //将整个rt结构,拷贝到返回结构指针p   
end;

//以下接收返回的结构时出现错误
var data : ^TResponse;
begin
      data := getData();
      rtArr := data.Buffer;
      n := rtArr.size;

      ListBox2.Items.Clear;
      for i:=0 to n-1 do begin
          ListBox2.Items.Add( IntToStr(rtArr.p[i]) );//执行到此处出现内存操作错误的提示
      end;
end;

我试过,如果data.Buffer光是一个数组、字符串、或固定长度的结构的话不会有问题。
但是现在我必须将一个动态数组放入data.Buffer传出去。不知道该如何做。

就相当于一个指针指向一个结构,而这个结构中又有一个指针指向另一个结构,而这另一个结构中有一个元素是动态数组。

Faint!!!
没人回答呀?
我自己已经搞定了,不得不放弃使用动态数组,而改用指针数组。
不过这样一换好像效率提高了,自己也长了不少知识。

使用move进行内存拷贝时最好将目的和源都强制转换pointer型,呵呵。

欢迎继续讨论,别把我的分给糟蹋了。
我看了好久,一个问题是ListBox2.Items.Add( IntToStr(rtArr.p[i]) );
好像你的结构中没有P?第二个问题就是对于动态数组,为什么不用SetLength?
没有p是因为我打错了,把p改成arr就成了,不好意思
我是用SetLength来设置动态数组的长度的,只是此操作与问题没太大关系,所以省略了。
动态数组是delphi中比较特殊的类型,更多的象指针,如果它放在结构中,它始终只占4字节(指针大小),如果是数组的话,则会占用相应大小的字节数,所有两者是有很大区别的.在使用它的高级用法前必须了解其原理
不错
那这样说我就是不能在结构中的指针里使用动态数组了?
可用指针数组来替代有点乱七八糟的感觉。
不是不可以,只是访问它的数据时不能通过结构简单的来完成,举例:
type
  TRec1 = Record
    Arr: Array of Integer;
  end;
  TRec2 = Record
    Arr: Array[0..4] of Integer;
  end;
var
  Rec1: TRec1;
  Rec2: TRec2;
begin
  Rec1.Arr := VarArrayCreate([0,4],varInteger);
  ShowMessage(IntToStr(SizeOf(Rec1)));
  ShowMessage(IntToStr(SizeOf(Rec2)));
end;

你发现结构其实大小完全不一样了吧
另外,如何将一个Pchar拷贝到pointer中

var str : PChar;
    p : pointer;

我是该使用
move(str, p^, StrLen(str));
还是
move(str^, p^, StrLen(str));

另外读p^里的PChar时该怎么做?

已经给分了
test ok
在system单元中查StringToVarArray函数的实现,那里有MOVE的例子
备案号:鲁ICP备13029499号-2 说三道四 www.s3d4.cn 说三道四技术文摘