java 为什么可选参数必须出现在声明的末尾

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/2896106/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-10-29 23:19:55  来源:igfitidea点击:

Why optional parameters must appear at the end of the declaration

c#javalanguage-agnosticlanguage-designoptional-parameters

提问by Incognito

In all programming languages supporting optional parameters that I have seen there is a imitation that the optional parameters must appear at the end of the declaration. No required parameters may be included after an optional item. What is the reason for that ? I guess it can be compiler/interpreter requirement.

在我见过的所有支持可选参数的编程语言中,都存在一种模仿,即可选参数必须出现在声明的末尾。可选项目后不得包含任何必需参数。这是什么原因?我想这可能是编译器/解释器的要求。

采纳答案by Noon Silk

Well, if they were at the front, how would you detect when they've stopped being supplied? The only way would be if the variable type was different afterthe optional parameters. Bit of a weird requirement, so it makes sense that you just force them to be last (save the trouble of complex rules for detecting the "final" optional parameter).

好吧,如果他们在前线,您将如何检测何时停止供应?唯一的方法是可选参数之后变量类型是否不同。有点奇怪的要求,因此您只需强制它们放在最后是有道理的(省去​​检测“最终”可选参数的复杂规则的麻烦)。

Besides, it's the most natural way to do it when calling the function.

此外,这是调用函数时最自然的方式。

回答by J?rg W Mittag

This is just an arbitrary rule that the designers of those specific languages made. There is absolutely no technical reason why that restriction should be there.

这只是那些特定语言的设计者制定的任意规则。绝对没有技术上的理由为什么应该存在这种限制。

It works just fine in Ruby:

它在 Ruby 中运行良好:

def foo(m1, m2, o1='o1', o2='o2', *rest, m3, m4)
  return m1, m2, o1, o2, rest, m3, m4
end

foo(1, 2, 3, 4)
# => [1, 2, 'o1', 'o2', [], 3, 4]

foo(1, 2, 3, 4, 5)
# => [1, 2, 3, 'o2', [], 4, 5]

foo(1, 2, 3, 4, 5, 6)
# => [1, 2, 3, 4, [], 5, 6]

foo(1, 2, 3, 4, 5, 6, 7)
# => [1, 2, 3, 4, [5], 6, 7]

foo(1, 2, 3, 4, 5, 6, 7, 8)
# => [1, 2, 3, 4, [5, 6], 7, 8]

All mandatory arguments must be supplied:

必须提供所有强制性参数:

foo(1, 2, 3)
# => ArgumentError: wrong number of arguments (3 for 4)

Without the rest parameter, supplying more than number_of_mandatory + number_of_optional arguments is an error:

如果没有 rest 参数,提供超过 number_of_mandatory + number_of_optional 的参数是一个错误:

def bar(m1, m2, o1='o1', o2='o2',  m3, m4)
  return m1, m2, o1, o2, m3, m4
end

bar(1, 2, 3, 4, 5, 6, 7)
# => ArgumentError: wrong number of arguments (7 for 6)

Mandatory parameters at the beginning of the parameter list are bound from left-to-right from the beginning of the argument list. Mandatory parameters at the end of the parameter list are bound from right-to-left from the end of the argument list. Optional parameters are bound left-to-right from the beginning of the remaining argument list. All arguments left over are bound to rest arguments.

参数列表开头的强制参数从参数列表的开头从左到右绑定。参数列表末尾的强制参数从参数列表的末尾从右到左绑定。可选参数从剩余参数列表的开头从左到右绑定。剩下的所有参数都绑定到剩余参数。

回答by dmckee --- ex-moderator kitten

Consider a declaration like:

考虑如下声明:

int foo(float a, int b=0, int c=0, float d);

(notice how I've defined defult parameters in the middle of the list) which is subsequently called like

(注意我是如何在列表中间定义默认参数的)它随后被称为

foo(0.0,1,2.0)

What is the call? In particular has bor cbeen omitted?

什么叫?特别是已经b或被c省略?

Compiler designers can get around this by using named parameters

编译器设计者可以通过使用命名参数来解决这个问题

foo(a=0,c=0,d=2.0)

a feature available in python for instance.

例如,python 中可用的功能。

回答by Heinzi

Optional parameters at the end allow you to stop specifying parameters at some point, e.g.

最后的可选参数允许您在某些时候停止指定参数,例如

void Test(int a, optional int b = 0, optional int c = 0) { ... } 

Test(3);

If you make ca required parameter, you'd have to use syntaxes like this:

如果您设置c了必需参数,则必须使用如下语法:

Test(3, , 2);
Test(a := 3, c := 2);

The advantage of an optional parameter is that it can be treated as if it wasn't there. If the optional parameters are in the middle of the parameter list, this is not possible without "counting commas" or using an overly verbose syntax.

可选参数的优点是可以将其视为不存在。如果可选参数位于参数列表的中间,那么如果不“计算逗号”或使用过于冗长的语法,这是不可能的。

回答by Johannes Rudolph

Just guessing in the wild: It maybe has something to do with calling conventions (e.g. parameters are pushed on the stack left to right, optional parameters are simply left out in case they were not specified).

只是猜测:它可能与调用约定有关(例如,参数从左到右推入堆栈,可选参数在未指定的情况下被简单地排除在外)。

回答by cyborg

Java and C# don't have named parameters so you can't do:

Java 和 C# 没有命名参数,所以你不能这样做:

myfunction(param1='Meh', optionalParam=2)

You have to do:

你必须做:

myfunction('Meh', 2)

Otherwise

否则

myFunction(2, 'Meh')

Is ambiguous. How is the compiler supposed to know that you meant 2 to be in the optional parameter set?

是暧昧。编译器怎么知道你的意思是 2 在可选参数集中?