Skip to content

Code generated by pattern matching includes unnecessary (duplicate) evaluations #82063

@AlekseyTs

Description

@AlekseyTs

Consider the following code:

interface I1
{
    int F {get;}
}

class C12
{
    object Value => throw null;

    static bool Test1((object, int) u)
    {
        return u is (C12 and I1 and { F: 1 }, 2) or (I1 and { F: 1 or 2 }, 1);
    }   
}

Examine code generated for Test. The following is a de-compilation output produced by https://lab.razor.fyi.
It looks like the property reads at label1 and label2 redundant. The value read at label1 isn't even used.
The value read at label2 is used, but we could simply use value from local f, assigned at label0.
Note that i2 = (I1)item; operations on lines preceding label1 and label2 are redundant as well.
Even if the property reads were necessary, The value is already available in local i.

	private static bool Test1(ValueTuple<object, int> u)
	{
		object item = u.Item1;
		C12 c = item as C12;
		int item2;
		int f2;
		if (c != null)
		{
			I1 i = c as I1;
			if (i != null)
			{
label0:
				int f = i.F;
				I1 i2;
				if (f == 1)
				{
					item2 = u.Item2;
					if (item2 != 2)
					{
						i2 = (I1)item;
label1:
						f2 = i2.F;
						goto IL_0081;
					}
					goto IL_0088;
				}
				i2 = (I1)item;
label2:
				f2 = i2.F;
				goto IL_0074;
			}
		}
		else
		{
			I1 i2 = item as I1;
			if (i2 != null)
			{
				f2 = i2.F;
				if (f2 != 1)
				{
					goto IL_0074;
				}
				goto IL_0079;
			}
		}
		goto IL_008d;
		IL_0079:
		item2 = u.Item2;
		goto IL_0081;
		IL_008d:
		return false;
		IL_0074:
		if (f2 == 2)
		{
			goto IL_0079;
		}
		goto IL_008d;
		IL_0088:
		return true;
		IL_0081:
		if (item2 == 1)
		{
			goto IL_0088;
		}
		goto IL_008d;
	}

Metadata

Metadata

Assignees

Labels

Area-CompilersCode Gen QualityRoom for improvement in the quality of the compiler's generated codeFeature - Pattern MatchingPattern Matchinghelp wantedThe issue is "up for grabs" - add a comment if you are interested in working on it

Type

No fields configured for Bug.

Projects

No projects

Relationships

None yet

Development

No branches or pull requests

Issue actions