Skip to content

Commit a18788d

Browse files
committed
Remove redundant flags enum values.
1 parent fd8145f commit a18788d

File tree

3 files changed

+34
-20
lines changed

3 files changed

+34
-20
lines changed

src/CSharpScriptSerializer/EnumCSScriptSerializer.cs

Lines changed: 12 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -21,25 +21,24 @@ public override ExpressionSyntax GetCreation(object obj)
2121
: GetSimpleValue(name);
2222
}
2323

24-
protected virtual ExpressionSyntax GetCompositeValue(Enum obj)
24+
protected virtual ExpressionSyntax GetCompositeValue(Enum flags)
2525
{
26-
var simpleValues = new List<ExpressionSyntax>();
27-
var defaultValue = Enum.ToObject(Type, value: 0);
28-
foreach (Enum currValue in Enum.GetValues(Type))
26+
var simpleValues = new HashSet<Enum>(flags.GetFlags());
27+
foreach (var currentValue in simpleValues.ToList())
2928
{
30-
if (currValue.Equals(defaultValue))
29+
var decomposedValues = currentValue.GetFlags();
30+
if (decomposedValues.Count > 1)
3131
{
32-
continue;
33-
}
34-
35-
if (obj.HasFlag(currValue))
36-
{
37-
simpleValues.Add(GetSimpleValue(Enum.GetName(Type, currValue)));
32+
simpleValues.ExceptWith(decomposedValues.Where(v => !Equals(v, currentValue)));
3833
}
3934
}
4035

41-
return simpleValues.Aggregate((previous, current) =>
42-
SyntaxFactory.BinaryExpression(SyntaxKind.BitwiseOrExpression, previous, current));
36+
return simpleValues.Aggregate((ExpressionSyntax) null,
37+
(previous, current) =>
38+
previous == null
39+
? GetSimpleValue(Enum.GetName(Type, current))
40+
: SyntaxFactory.BinaryExpression(
41+
SyntaxKind.BitwiseOrExpression, previous, GetSimpleValue(Enum.GetName(Type, current))));
4342
}
4443

4544
protected virtual ExpressionSyntax GetSimpleValue(string name)

src/CSharpScriptSerializer/Extensions.cs

Lines changed: 7 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -5,20 +5,21 @@ namespace CSharpScriptSerialization
55
{
66
internal static class Extensions
77
{
8-
internal static IEnumerable<T> GetFlags<T>(this T flags)
8+
internal static IReadOnlyCollection<Enum> GetFlags(this Enum flags)
99
{
10-
var values = new List<T>();
11-
var defaultValue = Enum.ToObject(typeof(T), value: 0);
12-
foreach (Enum currValue in Enum.GetValues(typeof(T)))
10+
var values = new List<Enum>();
11+
var type = flags.GetType();
12+
var defaultValue = Enum.ToObject(type, value: 0);
13+
foreach (Enum currValue in Enum.GetValues(type))
1314
{
1415
if (currValue.Equals(defaultValue))
1516
{
1617
continue;
1718
}
1819

19-
if (((Enum)(object)flags).HasFlag(currValue))
20+
if (flags.HasFlag(currValue))
2021
{
21-
values.Add((T)(object)currValue);
22+
values.Add(currValue);
2223
}
2324
}
2425

test/CSharpScriptSerializer.Tests/RoundTrippingTest.cs

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -148,7 +148,21 @@ public enum FlagsEnum
148148
Default = 0,
149149
FirstFlag = 1 << 0,
150150
SecondFlag = 1 << 1,
151-
ThirdFlag = 1 << 2
151+
ThirdFlag = 1 << 2,
152+
SecondAndThird = SecondFlag | ThirdFlag,
153+
FourthFlag = 1 << 3
154+
}
155+
156+
[Fact]
157+
public void Combined_flag_enum()
158+
{
159+
var input = FlagsEnum.FirstFlag| FlagsEnum.SecondAndThird;
160+
var script = CSScriptSerializer.Serialize(input);
161+
var output = CSScriptSerializer.Deserialize<FlagsEnum>(script);
162+
163+
Assert.Equal(input, output);
164+
Assert.Equal(typeof(RoundtrippingTest).Name + "." + typeof(FlagsEnum).Name + "." + FlagsEnum.FirstFlag + " | "
165+
+ typeof(RoundtrippingTest).Name + "." + typeof(FlagsEnum).Name + "." + FlagsEnum.SecondAndThird, script);
152166
}
153167

154168
[Fact]

0 commit comments

Comments
 (0)