Skip to content

Commit 9009384

Browse files
Used expression tree to GetName for enums.
1 parent f2f6462 commit 9009384

File tree

3 files changed

+42
-5
lines changed

3 files changed

+42
-5
lines changed

Source/EnumValue.cs

Lines changed: 27 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -40,11 +40,35 @@ public EnumValue(string value)
4040
/// <summary>
4141
/// Returns the string representation of the enum value.
4242
/// </summary>
43-
public override string ToString() => NameLookup[Value];
43+
public override string ToString() => NameLookup(Value);
4444

4545
internal static readonly (string Name, TEnum Value)[]?[] Lookup = CreateLookup();
4646

47-
internal static readonly ImmutableSortedDictionary<TEnum, string> NameLookup = CreateNameLookup();
47+
internal static readonly Func<TEnum, string> NameLookup = GetEnumNameDelegate();
48+
49+
static Func<TEnum, string> GetEnumNameDelegate()
50+
{
51+
var eValue = Expression.Parameter(typeof(TEnum), "value"); // (TEnum value)
52+
var tEnum = typeof(TEnum);
53+
var tResult = typeof(string);
54+
55+
return
56+
Expression.Lambda<Func<TEnum, string>>(
57+
Expression.Block(tResult,
58+
Expression.Switch(tResult, eValue,
59+
Expression.Block(tResult,
60+
Expression.Throw(Expression.New(typeof(Exception).GetConstructor(Type.EmptyTypes))),
61+
Expression.Default(tResult)
62+
),
63+
null,
64+
Enum.GetValues(tEnum).Cast<Object>().Select(v => Expression.SwitchCase(
65+
Expression.Constant(v.ToString()),
66+
Expression.Constant(v)
67+
)).ToArray()
68+
)
69+
), eValue
70+
).Compile();
71+
}
4872

4973
static (string Name, TEnum Value)[]?[] CreateLookup()
5074
{
@@ -267,6 +291,6 @@ public static bool TryParse<TEnum>(string value, bool ignoreCase, out TEnum e)
267291
/// <param name="value">The enum value to get the name for.</param>
268292
/// <returns>The name of the enum.</returns>
269293
public static string GetName<TEnum>(TEnum value) where TEnum : Enum
270-
=> EnumValue<TEnum>.NameLookup[value];
294+
=> EnumValue<TEnum>.NameLookup(value);
271295
}
272296
}

Source/Open.Text.csproj

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@
1717
<RepositoryUrl>https://github.com/Open-NET-Libraries/Open.Text</RepositoryUrl>
1818
<RepositoryType>git</RepositoryType>
1919
<PackageTags>dotnet, dotnetcore, string, span, readonlyspan, text, format, split, trim, equals, trimmed equals, first, last, preceding, following, stringbuilder, extensions</PackageTags>
20-
<Version>3.4.0</Version>
20+
<Version>3.4.1</Version>
2121
<PackageReleaseNotes></PackageReleaseNotes>
2222
<PackageLicenseExpression>MIT</PackageLicenseExpression>
2323
<PublishRepositoryUrl>true</PublishRepositoryUrl>

Tests/EnumValueTests.cs

Lines changed: 14 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ namespace Open.Text.Tests
55
{
66
public static class EnumValueTests
77
{
8-
enum Greek
8+
public enum Greek
99
{
1010
Alpha, Beta, Gamma
1111
}
@@ -35,6 +35,18 @@ public static void EvalValueParseFail(string value)
3535
Assert.False(EnumValue.TryParse<Greek>(value, true, out _));
3636
}
3737

38+
39+
[Theory]
40+
[InlineData(Greek.Alpha)]
41+
[InlineData(Greek.Beta)]
42+
[InlineData(Greek.Gamma)]
43+
44+
public static void GetName(Greek expected)
45+
{
46+
var s = expected.ToString();
47+
Assert.Equal(s, EnumValue.GetName(expected));
48+
}
49+
3850
static void CheckImplicit(EnumValue<Greek> value, Greek expected)
3951
{
4052
Assert.Equal(expected, value);
@@ -54,5 +66,6 @@ static void CheckImplicitCaseIgnored(EnumValueCaseIgnored<Greek> value, Greek ex
5466
Assert.False(value != expected);
5567
Assert.False(value != new EnumValue<Greek>(expected));
5668
}
69+
5770
}
5871
}

0 commit comments

Comments
 (0)