mirror of https://github.com/icsharpcode/ILSpy.git
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
68 lines
2.3 KiB
68 lines
2.3 KiB
#pragma warning disable CS9099, CS9100 |
|
using System; |
|
using System.Reflection; |
|
|
|
namespace ICSharpCode.Decompiler.Tests.TestCases.Correctness |
|
{ |
|
class LambdaOptionalAndParamsParameters |
|
{ |
|
static void Main() |
|
{ |
|
#if CS120 && !NET40 |
|
ReportMetadata(); |
|
ReportCalls(); |
|
#endif |
|
} |
|
|
|
#if CS120 && !NET40 |
|
delegate int OptionalFunc(int x = 5); |
|
|
|
delegate int PlainFunc(int x); |
|
|
|
delegate void ParamsAction(params int[] xs); |
|
|
|
delegate void PlainAction(int[] xs); |
|
|
|
// A lambda's parameter list does not have to repeat what the delegate declares: it may |
|
// state a different default, one the delegate does not have, or none where the delegate |
|
// has one, and the same for the params modifier. Metadata records what the lambda itself |
|
// declared, and reflection reports that rather than the delegate's, so the decompiled |
|
// lambda has to carry the lambda's own list back. |
|
static void Report(string name, Delegate d) |
|
{ |
|
ParameterInfo p = d.Method.GetParameters()[0]; |
|
Console.WriteLine("{0}: hasDefault={1} default={2} params={3}", |
|
name, |
|
p.HasDefaultValue, |
|
p.HasDefaultValue ? p.DefaultValue : "none", |
|
p.IsDefined(typeof(ParamArrayAttribute), inherit: false)); |
|
} |
|
|
|
static void ReportMetadata() |
|
{ |
|
Report("DefaultOnlyInDelegate", (OptionalFunc)((int x) => x * 2)); |
|
Report("DefaultOnlyInLambda", (PlainFunc)((int x = 3) => x * 2)); |
|
Report("DefaultDiffersFromDelegate", (OptionalFunc)((int x = 7) => x * 2)); |
|
Report("DefaultAgreesWithDelegate", (OptionalFunc)((int x = 5) => x * 2)); |
|
Report("ParamsOnlyInDelegate", (ParamsAction)((int[] xs) => Console.WriteLine(xs.Length))); |
|
Report("ParamsOnlyInLambda", (PlainAction)((params int[] xs) => Console.WriteLine(xs.Length))); |
|
} |
|
|
|
// The value a caller gets for an omitted argument comes from the delegate, never from the |
|
// lambda, so these stay the same whatever the lambda declared. |
|
static void ReportCalls() |
|
{ |
|
OptionalFunc noDefault = (int x) => x * 2; |
|
OptionalFunc otherDefault = (int x = 7) => x * 2; |
|
Console.WriteLine(noDefault()); |
|
Console.WriteLine(otherDefault()); |
|
Console.WriteLine(otherDefault(1)); |
|
|
|
ParamsAction expandedByDelegate = (int[] xs) => Console.WriteLine(xs.Length); |
|
expandedByDelegate(1, 2, 3); |
|
PlainAction notExpanded = (params int[] xs) => Console.WriteLine(xs.Length); |
|
notExpanded(new int[2]); |
|
} |
|
#endif |
|
} |
|
}
|
|
|