Skip to content

Commit

Permalink
two-fer: add dig deeper content (#2010)
Browse files Browse the repository at this point in the history
  • Loading branch information
ErikSchierboom authored Oct 31, 2022
1 parent b172e73 commit 4069cca
Show file tree
Hide file tree
Showing 11 changed files with 478 additions and 0 deletions.
21 changes: 21 additions & 0 deletions exercises/practice/two-fer/.approaches/config.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
{
"introduction": {
"authors": ["erikschierboom"]
},
"approaches": [
{
"uuid": "f567dfff-0f68-4226-b924-c6baf19babbf",
"slug": "optional-parameter",
"title": "Optional parameter",
"blurb": "Use an optional parameter and its default value.",
"authors": ["erikschierboom"]
},
{
"uuid": "e3999368-f13c-42e9-a814-e385356fd640",
"slug": "method-overloading",
"title": "Method overloading",
"blurb": "Use method overloading.",
"authors": ["erikschierboom"]
}
]
}
51 changes: 51 additions & 0 deletions exercises/practice/two-fer/.approaches/introduction.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,51 @@
# Introduction

The key to this exercise is to allow the `Speak()` method to be called _with_ and _without_ an argument.
There are two ways to do this in C#:

1. [Optional parameters][optional-parameters]
2. [Method overloading][method-overloading]

## General guidance

- Try to not repeat any string building logic ([DRY][dry])
- [String interpolation][article-string-formatting] is a great way to build strings

## Approach: optional parameter

```csharp
public static string Speak(string name = "you")
{
return $"One for {name}, one for me.";
}
```

For more information, check the [optional-parameter approach][approach-optional-parameter].

## Approach: method overloading

```csharp
public static string Speak()
{
return Speak("you");
}

public static string Speak(string name)
{
return $"One for {name}, one for me.";
}
```

For more information, check the [method overloading][approach-method-overloading].

## Which approach to use?

The optional parameter approach is not only more concise, it also more clearly encodes that name has a default value (which is not immediately apparent with the method overloading approach).

[optional-parameters]: https://learn.microsoft.com/en-us/dotnet/csharp/programming-guide/classes-and-structs/named-and-optional-arguments
[method-overloading]: https://www.pluralsight.com/guides/overload-methods-invoking-overload-methods-csharp
[approach-optional-parameter]: https://exercism.org/tracks/csharp/exercises/two-fer/approaches/optional-parameter
[approach-method-overloading]: https://exercism.org/tracks/csharp/exercises/two-fer/approaches/method-overloading
[article-optional-parameters-vs-method-overloading]: https://exercism.org/tracks/csharp/exercises/two-fer/articles/optional-parameters-vs-method-overloading
[article-string-formatting]: https://exercism.org/tracks/csharp/exercises/two-fer/articles/string-formatting
[dry]: https://en.wikipedia.org/wiki/Don%27t_repeat_yourself
Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
# Method overloading

```csharp
public static class TwoFer
{
public static string Speak()
{
return Speak("you");
}

public static string Speak(string name)
{
return $"One for {name}, one for me.";
}
}
```

First, let's define the `Speak()` method that has a single parameter for the name:

```csharp
public static string Speak(string name)
{
return $"One for {name}, one for me.";
}
```

Within the method, we use [string interpolation][string-interpolation] to build the return string where `{name}` is replaced with the value of the `name` parameter.

Then we define a second, parameterless method that calls the other `Speak()` method with `"you"` as its argument:

```csharp
public static string Speak()
{
return Speak("you");
}
```

The compiler will be able to figure out which method to call based on the number of arguments passed to the `Speak()` method.

## Shortening

We can shorten the methods by rewriting them as [expression-bodied methods][expression-bodied-method]:

```csharp
public static string Speak() =>
Speak("you");

public static string Speak(string name) =>
$"One for {name}, one for me.";
```

or

```csharp
public static string Speak() => Speak("you");

public static string Speak(string name) => $"One for {name}, one for me.";
```

## String formatting

The [string formatting article][article-string-formatting] discusses alternative ways to format the returned string.

## Optional parameters vs. method overloads

The main alternative to using method overloads is to use an [optional parameter approach][approach-optional-parameter]. If you're interested in how these two solutions compare to each other, go check out our [optional parameters vs method overloads article][article-optional-parameters-vs-method-overloading].

[approach-optional-parameter]: https://exercism.org/tracks/csharp/exercises/two-fer/approaches/optional-parameter
[article-optional-parameters-vs-method-overloading]: https://exercism.org/tracks/csharp/exercises/two-fer/articles/optional-parameters-vs-method-overloading
[article-string-formatting]: https://exercism.org/tracks/csharp/exercises/two-fer/articles/string-formatting
[optional-parameters-introduction]: https://learn.microsoft.com/en-us/archive/msdn-magazine/2010/july/csharp-4-0-new-csharp-features-in-the-net-framework-4#named-arguments-and-optional-parameters
[method-overloading]: https://www.pluralsight.com/guides/overload-methods-invoking-overload-methods-csharp
[string-interpolation]: https://learn.microsoft.com/en-us/dotnet/csharp/language-reference/tokens/interpolated
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
public static string Speak()
{
return Speak("you");
}
public static string Speak(string name)
{
return $"One for {name}, one for me.";
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
# Optional parameter

```csharp
public static class TwoFer
{
public static string Speak(string name = "you")
{
return $"One for {name}, one for me.";
}
}
```

We define a single `Speak()` method with one optional parameter: `name`.
This optional parameter has its default value set to the string `"you"`.
The caller of a method with an optional parameter can either pass in a value (which is then used) or not pass in a value (which caused the default value to be used).

These calls are thus identical:

```csharp
`Speak()`
`Speak("you")`
```

Within the method, we use [string interpolation][string-interpolation] to build the return string where `{name}` is replaced with the value of the `name` parameter.

## Shortening

We can shorten the method by rewriting it as an [expression-bodied method][expression-bodied-method]:

```csharp
public static string Speak(string name = "you") =>
$"One for {name}, one for me.";
```

or

```csharp
public static string Speak(string name = "you") => $"One for {name}, one for me.";
```

## String formatting

The [string formatting article][article-string-formatting] discusses alternative ways to format the returned string.

## Optional parameters vs. method overloads

The main alternative to using an optional parameter is to use a [method overloading approach][approach-method-overloading]. If you're interested in how these two solutions compare to each other, go check out our [optional parameters vs method overloads article][article-optional-parameters-vs-method-overloading].

[string-interpolation]: https://learn.microsoft.com/en-us/dotnet/csharp/language-reference/tokens/interpolated
[expression-bodied-method]: https://learn.microsoft.com/en-us/dotnet/csharp/programming-guide/statements-expressions-operators/expression-bodied-members#methods
[approach-method-overloading]: https://exercism.org/tracks/csharp/exercises/two-fer/approaches/method-overloading
[article-optional-parameters-vs-method-overloading]: https://exercism.org/tracks/csharp/exercises/two-fer/articles/optional-parameters-vs-method-overloading
[article-string-formatting]: https://exercism.org/tracks/csharp/exercises/two-fer/articles/string-formatting
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
public static string Speak(string name = "you")
{
return $"One for {name}, one for me.";
}
18 changes: 18 additions & 0 deletions exercises/practice/two-fer/.articles/config.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
{
"articles": [
{
"uuid": "9c9b759e-43c8-46ea-893d-59c310b84e21",
"slug": "optional-parameters-vs-method-overloading",
"title": "Optional parameters vs. method overloading",
"blurb": "Find out how optional parameters compare to method overloading.",
"authors": ["erikschierboom"]
},
{
"uuid": "bc651e10-b512-442c-a568-559867d31c91",
"slug": "string-formatting",
"title": "Formatting the return string",
"blurb": "Show the different ways in which the return string can be formatted.",
"authors": ["erikschierboom"]
}
]
}
Loading

0 comments on commit 4069cca

Please sign in to comment.