Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to set optional parameter without compile-time constant

Is there a way to write the C# method below:

public string Download(Encoding contentEncoding = null) {
    defaultEncoding = contentEncoding ?? Encoding.UTF8;
    // codes...
}

with a default parameter added so it looks like this:

public string Download(Encoding contentEncoding = Encoding.UTF8) {
    // codes...
}

without using a compile-time constant?

like image 542
cilerler Avatar asked Feb 09 '13 15:02

cilerler


People also ask

How do you specify an optional parameter?

Optional parameters are defined at the end of the parameter list, after any required parameters. If the caller provides an argument for any one of a succession of optional parameters, it must provide arguments for all preceding optional parameters. Comma-separated gaps in the argument list aren't supported.

Is it mandatory to specify a default value to optional parameter?

Every optional parameter in the procedure definition must specify a default value. The default value for an optional parameter must be a constant expression. Every parameter following an optional parameter in the procedure definition must also be optional.

Are optional parameters bad practice?

The thing with optional parameters is, they are BAD because they are unintuitive - meaning they do NOT behave the way you would expect it. Here's why: They break ABI compatibility ! so you can change the default-arguments at one place.

Can we make out parameter optional in C#?

No. To make it "optional", in the sense that you don't need to assign a value in the method, you can use ref . A ref parameter is a very different use case.


1 Answers

In short. No.

Optional parameters are required to be compile time constants or value types.

From Named and Optional Arguments (C# Programming Guide) on MSDN:

Each optional parameter has a default value as part of its definition. If no argument is sent for that parameter, the default value is used. A default value must be one of the following types of expressions:

  • a constant expression;
  • an expression of the form new ValType(), where ValType is a value type, such as an enum or a struct;
  • an expression of the form default(ValType), where ValType is a value type.

What you seem to want to achieve can be accomplished by overloading:

public string Download()
{
   return Download(Encoding.UTF8);
}

public string Download(Encoding contentEncoding)
{
   defaultEncoding = contentEncoding ?? Encoding.UTF8;
   // codes...
}

Note that this is not quite the same as optional parameters, as the default value gets hard coded into the caller with optional parameters (which is why the restrictions for them exist).

like image 191
Oded Avatar answered Oct 17 '22 02:10

Oded