Vimal CK
Vimal CK

Reputation: 3563

Why variable name as underscore character ("_") not working for Deconstruction

I have declared a variable as underscore character _ like below and the compiler able to execute the code smoothly.

 int _ = 10;
 _ += 10;

 onsole.WriteLine(_);

But, the compiler is not detecting the variable named as underscore character _ for a Deconstruction syntax shown below.

(string _, int age) = new Student("Vimal", "Heaven", 20);

At the same time, compiler and Visual Studio intellisense detect the variable named as underscore _ for another syntax shown below.

var student  = new Student("Vimal", "Heaven", 20);
(string _, int age) details = student.GetDetails();

Console.WriteLine(details._);

I understand that nobody use underscore character to name a variable. Why compiler is inconsistent in handling the underscore _ character?

I am not discussing about the C# discards here.

The Student class referred in the sample.

public class Student
{
    public string Name { get; set; }
    public string Address { get; set; }
    public int Age { get; set; }

    public Student(string name, string address, int age = 0) => (Name, Address, Age) = (name, address, age);

    public void Deconstruct(out string name, out int age) => (name, age) = (Name, Age);
    public (string, int) GetDetails() => (Name, Age);
}

Upvotes: 4

Views: 620

Answers (1)

Sweeper
Sweeper

Reputation: 273510

Why compiler is inconsistent in handling the underscore _ character?

In each of the first three code snippets, the _ character is interpreted a different way.

Here:

(string _, int age) details = student.GetDetails();

(string _, int age) is syntactically the type of the variable details, and the variable name is details, not _. _ is part of the type name, specifically the tuple field name.

From the docs (emphasis mine):

You indicate that a variable is a discard by assigning it the underscore (_) as its name.

So the _ in (string _, int age) details is not a discard. This is why you can access it as details._.

Later in the same page:

In C# 7.0, discards are supported in assignments in the following contexts:

  • Tuple and object deconstruction.
  • Pattern matching with is and switch.
  • Calls to methods with out parameters.
  • A standalone _ when no _ is in scope.

The situation you have here:

int _ = 10; 
_ += 10;

Console.WriteLine(_);

is not on the list, so discards do not apply there. In the first line, It is not "A standalone _", so _ is not a discard, and you declared a variable called _. In the following lines, there is a _ in scope, because you declared a variable with that name on the first line.

The second code snippet you showed:

(string _, int age) = new Student("Vimal", "Heaven", 20);

is a "Tuple and object deconstruction", which is on the list, so this time _ is treated as a discard, and this time it doesn't declare a variable called _.

Upvotes: 5

Related Questions