Reputation: 1211
My current code seems like this:
// for given methods like these:
// void Foo(Action<int> action)
// async Task DoAsync()
Foo(unusedInt =>
{
var unusedTask = DoAsync();
});
I know I can use the discard variable(_
) since C#7.0, like this:
Foo(_ =>
{
var unusedTask = DoAsync();
});
Or,
Foo(unusedInt =>
{
_ = DoAsync();
});
But I meet an error if I use _
for both of them:
Foo(_ =>
{
_ = DoAsync(); // error CS0029
});
error CS0029: Cannot implicitly convert type 'System.Threading.Tasks.Task' to 'int'
Is there anyway to discard both of the unused variables?
Or, can anyone confirm that it would not be possible within the current C# spec?
For reference,
If I omit the unusedTask
:
Foo(_ =>
{
DoAsync(); // warning CS4014
});
warning CS4014: Because this call is not awaited, execution of the current method continues before the call is completed. Consider applying the 'await' operator to the result of the call.
I'd like to avoid this warning, either.
Upvotes: -1
Views: 675
Reputation: 43845
When calling a method, a discard cannot be used in place of an argument, unless it is an out
argument. Nevertheless you could convey the same semantics by using a double underscore __
as the name of the parameter, to avoid the clash with any true discards used in the body of the method.
Foo(__ =>
{
_ = DoAsync();
});
The __
is not technically a discard. It is just a parameter name that communicates the intention of the programmer to ignore the value of the argument. Take a look at this article by Chris Mantle: Using underscore to denote unused parameters in C# lambdas.
Upvotes: 3
Reputation: 2574
You can use _
to discard a return value.
But intvalue with Foo((intvalue) =>
is not a return value (this is an anonymous method).
If you use _
then it is a normal parameter.
But you must be careful with _
to discard a Task
in your example.
Let me give you an example:
//Your async method
public async Task DoAsync()
{
Console.WriteLine("Start DoAsync");
await Task.Delay(2000);
Console.WriteLine("End DoAsync");
}
//a method that expects a Action-Delegate with 1 int as parameter
public void IntAction(Action<int> action)
{
action(2);
}
Now you can use this:
//Here the DoAsync wait 2 Seconds and then write 2 to Console
IntAction(async (intvalue) =>
{
await this.DoAsync();
Console.WriteLine(intvalue.ToString());
});
//Output is:
//Start DoAsync
//End DoAsync
//2
Or this:
//Here the DoAsync will not wait and write 2 to Console (discard Task)
IntAction(intvalue =>
{
_ = this.DoAsync();
Console.WriteLine(intvalue.ToString());
});
//Output is:
//Start DoAsync
//2
//End DoAsync
Upvotes: 1