简体   繁体   English

“var”和“out”参数有什么区别?

[英]What's the difference between "var" and "out" parameters?

What's the difference between parameters declared with var and those declared with out ?var声明的参数和用out声明的参数有什么区别? How does the compiler treat them differently (eg, by generating different code, or by changing which diagnostics it issues)?编译器如何区别对待它们(例如,通过生成不同的代码,或通过更改它发出的诊断)? Or do the different modifiers merely allow the programmer to document intended use of the parameters?或者不同的修饰符是否仅仅允许程序员记录参数的预期用途? What effect do the types of the parameters have on the matter?参数的类型对此事有何影响?

A var parameter will be passed by reference, and that's it. var参数将通过引用传递,就是这样。

An out parameter is also passed by reference, but it's assumed that the input value is irrelevant. out参数也通过引用传递,但假设输入值无关紧要。 For managed types, (strings, Interfaces, etc,) the compiler will enforce this, by clearing the variable before the routine begins, equivalent to writing param := nil . 对于托管类型(字符串,接口等),编译器将通过在例程开始之前清除变量来强制执行此操作,相当于编写param := nil For unmanaged types, the compiler implements out identically to var . 对于非托管类型,编译器实现out相同于var

Note that the clearing of a managed parameter is performed at the call-site and so the code generated for the function does not vary with out or var parameters. 请注意,清除托管参数是在调用站点执行的,因此为函数生成的代码不会随outvar参数而变化。

There is not much difference, for the compiler that is. 对于编译器来说没有太大的区别。 See Mason's answer for that. 梅森的答案

Semantically, there is a big difference: 在语义上,有一个很大的区别:

  • var tells the programmer that the routine could work with its current value, var告诉程序员该例程可以使用其当前值,
  • out tells the programmer that the routine will ignore/discard its current value. out告诉程序员该例程将忽略/丢弃其当前值。

Slightly late but just for the record, I came across a case where var or out made a big difference. 稍微迟到但仅仅是为了记录,我遇到了一个案例,其中varout产生了很大的不同。

I was working on a SOAP web service which exported the following method: 我正在开发一个SOAP Web服务,它导出了以下方法:

function GetUser( out User :TUser ) :TResult;

which was getting imported into C# as the equivalent of 它被导入到C#中,相当于

function GetUser( out Result :TResult) :TUser;

when I changed the out to a var it it imported correctly. 当我将out更改为var时 ,它正确导入。

I'm guessing that the Delphi SOAP invoker treats the function result as an out parameter and that having two out parameters confuses the Delphi SOAP routines. 我猜测Delphi SOAP调用程序将函数结果视为out参数,并且具有两个out参数会混淆Delphi SOAP例程。 I'm not sure if there is a workaround to allow you to use out parameters. 我不知道是否有一种变通方法,让你使用out参数。

I read earlier that out parameter is set to default by called function, but today I realized that it is not completely true.我之前读到,out 参数被称为 function 设置为默认值,但今天我意识到这并不完全正确。 Value of out parameter is discarded by called routine, but if that routine does not change its value, caller can still get it initial value, which was assigned before passing to called thread. out 参数的值被调用的例程丢弃,但如果该例程没有改变它的值,调用者仍然可以获取它的初始值,该初始值在传递给被调用线程之前分配。

For example:例如:

procedure JustNothing(out x : integer);
begin
  // do nothing
end;

procedure TestOutVar;
var i : Integer;
begin
  i := 100;
  JustNothing(i); // after this call, i will still be 100
end;

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM