Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/csharp-4.0/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Parameters 具有可选参数的冲突重载方法_Parameters_C# 4.0_Overloading_Optional Parameters - Fatal编程技术网

Parameters 具有可选参数的冲突重载方法

Parameters 具有可选参数的冲突重载方法,parameters,c#-4.0,overloading,optional-parameters,Parameters,C# 4.0,Overloading,Optional Parameters,我有两个重载方法,一个带有可选参数 void foo(string a) { } void foo(string a, int b = 0) { } 现在我呼吁: foo("abc"); 有趣的是,第一个重载被称为。 为什么不将可选值设置为零的第二个重载 老实说,我希望编译器会带来一个错误,至少是一个警告,以避免无意中执行错误的方法 这种行为的原因是什么?为什么C#团队会这样定义它?不需要自动填写任何可选参数的重载比需要自动填写的重载更可取。但是,在自动填充一个参数和填充多个参数

我有两个重载方法,一个带有可选参数

void foo(string a)  { }  
void foo(string a, int b = 0) { }  
现在我呼吁:

 foo("abc");
有趣的是,第一个重载被称为。 为什么不将可选值设置为零的第二个重载

老实说,我希望编译器会带来一个错误,至少是一个警告,以避免无意中执行错误的方法


这种行为的原因是什么?为什么C#团队会这样定义它?

不需要自动填写任何可选参数的重载比需要自动填写的重载更可取。但是,在自动填充一个参数和填充多个参数之间没有这样的偏好-例如,这将导致编译时错误:

void Foo(int x, int y = 0, int z = 0) {}
void Foo(int x, int y = 0) {}
...
Foo(5);
请注意,Foo(5,5)将解析为第二种方法,因为这样就不需要自动填写任何可选参数

根据C#4规范第7.5.3.2节:

否则,如果MP的所有参数 相应的论点 默认参数必须是 替换至少一个可选的 MQ中的参数则MP优于 MQ

老实说,我认为在大多数情况下,这是大多数人所期望的行为。在混合中引入基类方法时会变得很奇怪,但情况一直如此。

来源:

如果两个候选者被判定为同等优秀,则优先选择没有可选参数的候选者,因为调用中省略了这些参数。这是因为对于参数较少的候选者,重载解析的一般偏好


想象一下,如果情况正好相反。你有一份申请。它有一个方法:

void foo(string a)  { }   
一切都很顺利。现在,您需要添加一个带有可选参数的重载:

void foo(string a, int b = 0) { }  
轰!所有方法调用都转到新方法。不管你想不想,随时都可以。添加方法重载可能会在整个应用程序中导致错误的方法调用

从我的角度来看,在这种情况下,您将有更多的机会来破解您(或其他人)的代码

而且,在4.0版之前,它在C#中一直被忽略,但您可以使用它。有些人确实在C代码中使用它来支持与其他语言的某些互操作性场景,如Visual Basic或COM互操作。现在C#将其用于可选参数。添加警告/错误可能会导致这些应用程序发生重大更改


可能还有其他原因,但这正是我首先想到的。

谢谢你的回答。还有一个问题:他们为什么这样定义它?是否存在一种场景,其中带有可选参数的重载是有意义的?它永远不会用默认值调用,对吗?但这可能会导致不必要的错误。我仍然认为编剧至少应该给出一个警告。还有其他一些例子,开发人员必须明确地告诉编译器他知道自己在做什么。例如,如果方法中的一个参数被声明为ref,我也需要在方法调用中显式使用ref关键字;否则它就无法编译。@Thomas:恐怕我对其原理没有任何答案——尽管埃里克·利珀特可能会这样做。我不想让你在电话号码上再加上任何行李——毕竟,使用默认参数的原因正是为了减少所需的代码量。它应该显示编译器错误或代码分析警告。@Loctus您似乎没有阅读Alexandra答案的倒数第二段。这正是导致潜在错误的糟糕语言设计。它也很容易被内幕人士利用来进行公司间谍活动。我希望他们能阻止语言已经允许这样做。