使用可选参数

时间:2012-11-09 13:56:14

标签: c# optional-arguments

我有一个带有2个可选参数的方法。

public IList<Computer> GetComputers(Brand? brand = null, int? ramSizeInGB = null)
{
    return new IList<Computer>();
}

我现在正尝试在其他地方使用此方法,我不想指定Brand参数而只是int,但我使用此代码时出错:

_order.GetComputers(ram);

我收到的错误:

Error   1   The best overloaded method match for 'ComputerWarehouse.Order.GetComputers(ComputerWarehouse.Brand?, int?)' has some invalid arguments  C:\Users\avmin!\Documents\InnerWorkings Content\630dd6cf-c1a2-430a-ae2d-2bfd995881e7\content\T0062A2-CS\task\ComputerWarehouse\ComputerStore.cs 108 59  ComputerWarehouse
Error   2   Argument 1: cannot convert from 'int?' to 'ComputerWarehouse.Brand?'    C:\Users\avmin!\Documents\InnerWorkings Content\630dd6cf-c1a2-430a-ae2d-2bfd995881e7\content\T0062A2-CS\task\ComputerWarehouse\ComputerStore.cs 108 79  ComputerWarehouse

3 个答案:

答案 0 :(得分:9)

如果要跳过其他可选参数,则必须指定可选参数的名称。

_order.GetComputers(ramSizeInGB: ram);

答案 1 :(得分:5)

要允许编译器填充早期的参数,您需要指定后面的名称:

_order.GetComputers(ramSizeInGB: ram);

基本上,C#编译器假定除非您指定任何参数名称,否则您提供的参数将按其他顺序排列。如果您没有为所有参数提供值,并且其余参数具有默认值,则将使用这些默认值。

因此所有这些都是有效的(假设brandram的适当值):

_order.GetComputers(brand, ram);       // No defaulting
_order.GetComputers(brand);            // ramSizeInGB is defaulted
_order.GetComputers(brand: brand);     // ramSizeInGB is defaulted
_order.GetComputers(ramSizeInGB: ram); // brand is defaulted
_order.GetComputers();                 // Both arguments are defaulted

答案 2 :(得分:2)

正确的语法是将命名参数与可选参数结合使用,如下所示:

_order.GetComputers(ramSizeInGB: ram);

只有当它们位于指定的参数之后时,才可以跳过可选参数(不使用命名参数),所以这样就可以了:

_order.GetComputers(new Brand());

就像这个

_order.GetComputers();

要了解为什么必须以这种方式完成,请考虑具有如下签名的方法:

public void Method(double firstParam = 0, long secondParam = 1)

Method(3);

此处编译器无法推断开发人员是否打算使用第一个参数或第二个参数调用该方法,因此区别的唯一方法是明确说明哪些参数映射到哪些参数。