问题
Consider the following C# function:
void DoWork()
{
...
}
The C# documentation states:
When used as the return type for a method, void specifies that the method does not return a value.
That seems straight-forward enough and, in most cases, that suits as a fair definition.
However, for many lower-level languages (i.e. C) "void" has a slightly different meaning. Specifically, all blocks of code must return something. Therefore, void
is a representation of the null pointer which is a representation of "nothing". In such a case, you do not need to have a return
statement within your code because any block-statement that doesn't return a value automatically returns a null pointer.
Is this what C# does or when a void
function is called, does it execute a block of code and return without even having a pointer containing a value of void?
回答1:
First off, C# is compiled into IL, so the final representation post-JIT may differ.
With a void method, the method signature in IL will be marked as void
, and the ret
opcode will still exist. This means, from the standpoint of IL, the "returned" value on the call stack may or may not exist, but it will never get copied and used on the call site. The ret
opcode will only push a return value if it exists, and this is not required to exist in a void
returning method, so in many cases, it will not return anything, even in a low level conceptual standpoint.
However, for many lower-level languages (i.e. C) "void" has a slightly different meaning. Specifically, all blocks of code must return something.
This is not the case in the CLR. A void method can truly return nothing, as the ret
opcode is allowed to not return anything. See OpCodes.Ret:
Returns from the current method, pushing a return value (if present) from the callee's evaluation stack onto the caller's evaluation stack.
回答2:
If this spec is anything like the official language specification, return value for void methods/functions is not defined, which means that, if you want a null value, it's best to explicitly use null rather than this.
In C, it is bad form to use the return value from a void function to get a null. This is because:
- It will be confusing to the next guy,
- It makes no sense. If you want null, use null. If you want the void function to return a value based on its computation, don't use a void return type, and
- Most importantly, since it is technically incorrect, even if the code compiles on the current version of your compiler, it may not compile at all in future versions, or the behavior may unexpectedly change.
edit: Additionally, if the word assembly
doesn't send cold shivers up your spine...
In the underlying x86 assembly code that C compiles into, void functions really can return nothing. The idea of returning a value from a function is actually implemented by the compiler, so if you tell the compiler you don't want something to have a return value, there won't be one.
This document has a nice explanation of the ret
instruction and how it fits into subroutine calling convention (unfortunately id
elements are few and far between in this document, so it takes a bit of scrolling. But it's in there. Search for ret
on the page).
回答3:
In MSIL, Ret can optionally return a value, so void methods doesn't return anything. See http://msdn.microsoft.com/en-us/library/system.reflection.emit.opcodes.ret.aspx
I'm not sure how this is handled when MSIL is JIT-ed.
来源:https://stackoverflow.com/questions/18260043/return-nothing-or-return-void-what-exactly-does-c-sharp-do-at-the-end-of-a-voi