关于指针地址操作(50分)

to creation-zy:
你说的没有错,Delphi的传值方式确实容易让人混淆,我也吃过亏,被整惨了。
不过,我想主要是我们太熟悉C++造成的,不能完全怪Delphi,如果一个不会C++
的直接人学习Delphi,我想会好得多。对于你的以下代码
> mov edx,PBuf
> mov eax,PSrcBuf
> mov ecx,len
> call move
我想有几个问题
1。看你的程序的人必须会使用汇编,否则看不懂
2。必须知道Delphi的参数传递的顺序以及是使用的的什么寄存器
3。如果Delphi编译器升级后改变了参数传递的方法或寄存器,你的代码就必须重写,也就是说
可移植性差
 
type
PHuman = ^THuman;
THuman = record
name: array [0..20]of char;//这里不能使用string,当然如果一个程序中可以,如果不是在一个程序中呢,自己好好想想,不懂再说.
age: integer;
sexy: boolean;
end;


procedure TForm1.Button1Click(Sender: TObject);
var
c: PChar;
c1: string;
h, h1, h2, h3: THuman;
p: Pointer;
begin
h.name := 'oh,my God!';
h.age := 100000;
h.sexy := true;
try
GetMem(c, sizeof(h));
Move(h, c^, sizeof(h));
ShowMessage('phuman(c)=' + PHuman(Pointer(c))^.name);
Move(c^, h1, sizeof(h1));
showMessage('h1.name=' + h1.name);
finally
FreeMem(c);
end;

SetLength(c1, sizeof(h1));
p := @c1[1];// p := Pointer(c1);
// Move(h, p, sizeof(h));//这是错误的
Move(h, Pointer(c1)^, sizeof(h));//最快的方法
// Move(h, PChar(c1)^, sizeof(h));//这才是正确的。次之。
// Move(h, c1[1], sizeof(h));//这也是正确的。最慢地方法。
Caption := Format('@c1[1]=%p, Pointer(c1)= %p, PChar(c1)= %p, PChar(c1)^= %s',
[@c1[1], Pointer(c1), Pointer(PChar(c1)), (PChar(c1)^)]);
ShowMessage('phuman(c1)=' + PHuman(Pointer(c1)).name);
h3 := PHuman(Pointer(c1))^;
ShowMessage('h3.name' + h3.name);
Move(pchar(c1)^, h2, sizeof(h2));
ShowMessage('h2.name=' + h2.name);
end;
 
起了怪了,这么地回答,居然无切题者.[:(][?]
 
青菜罗卜,各有所爱,哈哈!!
 
[:D] 收了此贴!
 
type testrec = packed record
a : integer
b : integer ;
end;
..................
var
test1,test2 : testrec ;
buf : array [0..64] of char ;
begin
test1.a := 10
test1.b := 20;
copymemory(@buf,test1,sizeof(testrec )) // 等同于 memcpy
copymemory(@test2,@buf,sizeof(testrec ))
//test1 test2 是一样了
end;
 
给分吧
我也湖涂了:)
 
啊,上面的太深奥了,有点看不懂,有没有关于指针的比较简单的,通用的介绍.还有那些时候我门在写delphi程序的时候要用到指针?
 
幸亏我不太精通C++,呵呵
 
memset========>AllocMem(长度);返回地址.(或者GeMem(地址指针,长度))
memcpy========>CopyMemory(目标地址指针1,源地址指针2,长度);
 
Mark and Study
 
老兄们还是好好看看Delphi帮助
long string types
pchar
getmem
freemem
new
dispose
reallocmem
finalize
 
用windows api相关函数,这样你就不用考虑不同语言之间的差异了
 
关注这个帖很久了,但是始终没有我感觉兴趣的回答。
我想问一下,Move与CopyMemory只适合于内存的拷贝。对于拷贝对象如果存在指针,有没有办法重建对象。
举例说明就是:
type
PHuman = ^THuman;
THuman = record
name: array [0..20]of char;
age: integer;
sexy: boolean;
int : array of integer
//关键在这里。动态分配的数组,在结构中是以指针存放的。
end;
var
h: THuman;
C1 : string;
begin
h.name := 'oh,my God!';
h.age := 100000;
h.sexy := true;
setlength(h.int,3);
h.int[0] := 0;
h.int[1] := 1;
h.int[2] := 2;
SetLength(c1, sizeof(h));
Move(h, Pointer(c1)^, sizeof(h));//最快的方法
h.name := '(^..^)';
h.int[0] := 3;
h.int[1] := 4;
h.int[2] := 5;
//这时候,PHuman(Pointer(c1))^.name还是My God!,但是PHuman(Pointer(c1))^.int[0]的内容也变成了h.int[0]的内容了。
我希望PHuman(Pointer(c1))^.int[0]保持0。
各位有没有好办法?我不想一个个单元的复制。

end;
 
To keenhzh:
你既然知道int是一个指向动态数组的指针,复制整个结构之后c1里的int和h.int都是指向同一块内存地址,你要让c1.int的内容和h.int的内容不一样,就得手动再为c1.int分配一块内存。
 
to:bluely:
呵呵,我就想有没有偷懒的办法:)
我现在手头开发的一个东西,结构很复杂,里面套着无数个动态数组;又要经常涉及结构的复制,不想一个个的分配再复制。

 
遗憾的是没有。。即使是C++,对于动态也是一样要手动复制和分配。
不过 << --结构很复杂,里面套着无数个动态数组
这个恐怕是另外一个问题引起的,就是系统分析没做好,对数据结构的设计比较混乱造成的,如果有好的系统分析,应该是不会出现这种情况的。你的结构再复杂,能比几千个windows API里面用到的数据结构还复杂吗?windows Api还不是井井有条的,所以。这就是设计的问题了
 

Similar threads

X
回复
0
查看
772
xalion
X
S
回复
0
查看
645
SUNSTONE的Delphi笔记
S
S
回复
0
查看
655
SUNSTONE的Delphi笔记
S
顶部