我们经常使用result的函数返回值,有谁能够从作用域,生命期,初始值等几个方面谈一下result。(50分)

H

hygsxy

Unregistered / Unconfirmed
GUEST, unregistred user!
如题目。
 
作用域当然是在当前函数内部,生命期就是这个函数运行时间内。初始值没有意义,因为result在运行时不一定占用内存,严格来说result就是退出函数那一瞬间的eax寄存器值,编译器会根据需求生成语句动态调整保存函数运行过程中用到的result值的地方(比如临时移动到ebx寄存器,或者push进堆栈等)。
 
我有点事,先走一步,晚上我会贴出一段使用 result的代码,或许你会发现,结果并不像你想的那样。
 
估计楼主要贴的是体现前一次调用的result对后一次调用有影响或者返回值等于参数值之类的代码.
现在对楼主的帖子偶都不太敢回,因为最近比较敏感,怕又引起什么大的"讨论".[:D]
 
to Another_eYes大侠:
1.若调用一个没有给Result赋值的函数,会如何?
2.若在函数结束之前给result赋值,它又如何存储?

在看一看上面的回答,好象有点明白了啊,不知楼主要贴什么啊?
 
hygsxy好像又有高论了,呵呵,排队来的
 
to All:
还是希望大家一讨论技术为目的.
这个问题是值得讨论的.
 
我也是来听课的啊,了解这些不会坏的。[8D]
 
Another_eYes大虾的话是有一定的道理的,比如,你在调用一个返回值为Boolean的方法前(该方法内部不赋Result),先给EAX进行赋值(不知道是不是这个寄存器,手边没DELPHI),通过赋不同的值,该函数的结果不同,
另外,以前也碰到过一些情况,Result进行累加时,如
function A: Integer;
begin
Result := Result + 1;
end;
Result 的值经常会是上一次的值, 至于在调用之前更改EAX的值,倒没有试过,哪位手边有delphi可以尝试一下
 
呵呵,如果你要告诉我什么未赋值的result是一个可以预测的值的话就不必了,我可以告诉你原因: 因为大家一般写这种小测试代码的话喜欢写成一个类方法,那么我有幸告诉您,类方法传递的参数比你参数表中的多一个(也就是第一个参数),即类实例的self指针,hoho,根据delphi传递参数的调用约定,这个值是通过EAX传递的,如果你函数中代码很简单,没有马上修改这个EAX的话那么你的result目前就是self,不过不幸的是这是不可预测的,也就是说在你第一个访问result的语句前极有可能delphi会插入一堆处理代码,尤其是传递参数个数超过3个(类方法参数超过2个时),delphi也许会对堆栈中的参数进行某些处理(最常见的就是传递的字符串的引用计数操作),看过delphi反编译汇编码的都知道,这些中间操作时delphi首先使用的寄存器就是EAX(而且有时看得很郁闷的是它会将EAX中有用的数据先移到其它寄存器或堆栈中,然后就用EAX来作为其它操作的中间寄存器,即使那时EBX, ECX等寄存器空着没用),造成的结果就是等你访问那个result时已经不是你期望的值了。
 
养成好习惯,不要在Result未操作赋值之前返回.
作用域/生命期 不用讲了吧.
初始值 这个从逻辑上是没有意义的.就如同out参数的初始值一样.即使有,也只能是这个版本的特性如此,谁也不敢保证下一个版本是否还是这样.
 
请大虾们继续发表高见啊!

另:to qiubole:
今天看见你在为一家河南的公司招人啊,我是河南的,有点感兴趣啊!
 
不好意思,这么晚了才把代码贴上来,只因本人的项目设计马上要审查的缘故,理解一下。呵呵。。。。。。。。
是啊。其实看起来result不算一个问题,要深究的话还是有东西可挖掘的。
LeeChange兄
只要是在讨论技术的,说说都无妨。你预测的基本上是我要提的。这是个DFW提的问题,但没有一个好的解释,不妨大伙讨论一下。我不喜欢把分纂着,总喜欢想到什么就问什么问题。
function TForm1.mytest(i:integer):string;
begin
result:=result+','+inttostr(i);
end;

procedure TForm1.Button1Click(Sender: TObject);
var
i:integer;
abc:string;
begin
for i:=1 to 6 do
begin
abc:=mytest(i);
end;
showmessage(abc);
end;
测试一下,看最后的结果是什么?现在的result起了个什么作用?
 
我不明白研究这个问题有什么意义。
这个问题的答案能给我们带来什么。
效率?简洁的代码?
唯一的好处是知道可以这样做,但是不能用来做任何实质性的东西。
不能为提高代码效率。
不能为提高编码效率。
不能使代码简洁。
不能使代码易懂。
不能增加程序稳定性。

何苦来着?
 
请楼主测试一下.
function TForm1.mytest(i: integer): string;
begin
result:=IntToHex(Integer(@result), 8);
end;

procedure TForm1.Button1Click(Sender: TObject);
var
i:integer;
abc:string;
begin
abc:=mytest(i);
Caption:= IntToHex(Integer(@abc), 8) +','+abc;
end;

Result在逻辑上就应当是一个out参数,任何初始值都是逻辑上毫无意义的.我印象在C#当中如果一个类的字段在没有被初始化之前是不允许使用的。当Delphi跨到.NET时代,一切都是对象,不是指针的时候.编译器和规则必然有很大的变化,这个技巧恐怕不能再用下去的.
 
浮冰之上盖洋房
 
本人一直不看好DELPHI中的不赋初始值的问题,这种习惯很不好,在DELPHI的程序中,很多问题都是因为未赋初始值才会产生的!
 
I faint. 又有人把未初始化这类考虑不完备才造成的莫名其妙的问题提到台面上来了。
我可能没时间再将重复过N次的话再多说一遍了。都什么年头了,还在讨论这类不着边际
的问题。一个合格的程序员应该尽可能用语言无关的思路思考问题,有了思考结果后,再用
严格按照特定语言编程规范(包括隐含的规范)的方法编写具体代码。按照这个方法,就不
会出现这类莫名其妙的戏论。
 
to 龙丹
兄弟这句话 言间意深啊

同意 一剑封喉 的说法
你的result 没有初始化, 当然什么事都能发生

function TForm1.mytest(i:integer):string;
begin
result:='' //你加上这句看看有什么问题
result:=result+','+inttostr(i);
end;

procedure TForm1.Button1Click(Sender: TObject);
var
i:integer;
abc:string;
begin
for i:=1 to 6 do
begin
abc:=mytest(i);
end;
showmessage(abc);
end;
 

Similar threads

S
回复
0
查看
3K
SUNSTONE的Delphi笔记
S
S
回复
0
查看
2K
SUNSTONE的Delphi笔记
S
D
回复
0
查看
917
DelphiTeacher的专栏
D
D
回复
0
查看
2K
DelphiTeacher的专栏
D
D
回复
0
查看
2K
DelphiTeacher的专栏
D
顶部