1. Default Values for Parameters
Imagine a coffee shop: if you don't say whether you want sugar in your coffee, the barista will add one spoon by default. But sometimes you want... two! Or none at all (heroic!). It's the same with methods: sometimes it's handy for some parameters to take standard values if you don't specify them.
And named arguments are like being able to say in your coffee order: "And I want soy milk, not regular," no matter what order the ingredients usually go in.
In C# both of these features make your code cleaner, more convenient, and help protect you from bugs. You'll see them a lot in real projects: from .NET libraries to popular frameworks — that's why employers love to see you use them confidently.
Syntax
A default value for a function parameter is set right in the method declaration using the = sign. If you don't specify this parameter when calling the method, the default value is used.
void PrintStudent(string name, int age = 18)
{
Console.WriteLine($"Student: {name}, age: {age}");
}
How does it work?
- If you call PrintStudent("Alisa"); — it will print: Student: Alisa, age: 18.
- If you call PrintStudent("Sasha", 22); — it will print: Student: Sasha, age: 22.
Does it work for any types?
You can set a default value for any parameter type, but there are some details:
- For reference types (string, classes, etc.): you can use null or a specific literal as the default.
- For value types (int, double, bool, etc.): you specify a literal of the needed type.
- For enums (enum), structs: you can also use default values.
void AddStudent(string name, int course = 1, double averageScore = 5.0, string comment = null)
{
Console.WriteLine($"Added student: {name}, course: {course}, average score: {averageScore}, comment: {comment}");
}
Calls:
- AddStudent("Ivan");
- AddStudent("Maria", 2);
- AddStudent("Fyodor", 2, 4.7, "With honors");
Order of parameters with default values
All optional parameters (with default values) must go to the right (after all required ones). If you try to put a parameter with a default value before a required one, the compiler will slam the door in your face.
// Error!
void Test(int a = 1, int b)
{
// ...
}
Why is that? Because otherwise the compiler can't figure out which argument goes to which parameter when you call the method.
2. Named Arguments
By default, when you call a method and pass arguments, their order must exactly match the order of parameters in the method definition. But sometimes the list is long, some parameters have default values, and it's easy to mess up.
Named arguments let you explicitly specify which argument goes to which parameter, in any order.
AddStudent(name: "Elizaveta", averageScore: 4.2, comment: "Best student of the semester");
- Here we don't specify the course (course), so it'll be 1 (the default).
- No need to remember which number the comment parameter was — just use its name.
You can even swap the parameters around:
AddStudent(averageScore: 3.7, name: "Georgiy");
This is super convenient, and your code gets way more readable!
Mixing with positional arguments
You can mix named and positional arguments (without a name), but all positional ones must go before the named ones.
// Correct
AddStudent("Sergey", averageScore: 4.9);
// Error
AddStudent(course: 2, "Filipp");
After the first named parameter, everything else must be named too. The compiler is strict about this order to protect you from surprises.
Handy for methods with lots of parameters
This is a common trick when using methods that have a ton of extra options. For example, if you were writing a function to add a user somewhere in a cloud database:
void RegisterUser(
string username,
string password,
string email = null,
bool admin = false,
bool sendWelcomeEmail = true,
string language = "ru"
)
A call without named arguments would look scary:
RegisterUser("cat", "qwerty", null, false, true, "ru");
With named arguments, it's all readable and safe:
RegisterUser("cat", "qwerty", admin: true, sendWelcomeEmail: false, language: "en");
Tip: use named arguments so your code is readable even without docs!
3. Implementation Details and Common Mistakes
When you're just starting to use default values and named arguments, it's easy to mess up in a few places.
- Parameter order. Always put parameters with default values after the required ones. If you swap them, the compiler will throw an error.
- Changing the default value in a library. If you change the default value in a library, old clients won't automatically start using the new one. The default value gets compiled into the calling code. So think before you change defaults in public libraries.
- Mixing positional and named arguments. If you mix positional and named, but after a named one you try to specify a positional again — it won't work. For example: Func(a: 1, 2) — will throw an error.
- Typo in parameter name. The compiler is strict here: if you mess up the letters (like writing naem: "Misha"), you'll get an error like: "No such parameter, what are you even doing?!".
GO TO FULL VERSION