using System;
using System.Reflection;
public delegate bool TryParser<T>(string s, out T result);
public static class Parser
{
public static bool TryParse<T>(string s, out T result)
{
return Inner<T>.parser(s, out result);
}
public static T? ParseOrNull<T>(string s)
where T : struct
{
T result;
if (TryParse<T>(s, out result)) return result;
else return null;
}
static class Inner<T>
{
public static TryParser<T> parser;
static Inner()
{
var m = typeof(T).GetMethod("TryParse", new[] { typeof(string), typeof(T).MakeByRefType() });
if (m == null)
throw new NotSupportedException();
parser = (TryParser<T>)Delegate.CreateDelegate(typeof(TryParser<T>), m);
}
}
}
class Program
{
static void Main()
{
Console.WriteLine(Parser.ParseOrNull<int>("1234"));
Console.WriteLine(Parser.ParseOrNull<int>("12a34"));
Console.WriteLine(Parser.ParseOrNull<int>("12344aq"));
Console.WriteLine(Parser.ParseOrNull<int>("123safw4"));
Console.WriteLine(Parser.ParseOrNull<double>("1.234"));
Console.WriteLine(Parser.ParseOrNull<double>("12.34"));
Console.WriteLine(Parser.ParseOrNull<double>("12.a34"));
Func<string, byte?> parser = Parser.ParseOrNull<byte>;
Console.WriteLine(parser("255"));
}
}
dXNpbmcgU3lzdGVtOwp1c2luZyBTeXN0ZW0uUmVmbGVjdGlvbjsKCnB1YmxpYyBkZWxlZ2F0ZSBib29sIFRyeVBhcnNlcjxUPihzdHJpbmcgcywgb3V0ICBUIHJlc3VsdCk7CgpwdWJsaWMgc3RhdGljIGNsYXNzIFBhcnNlcgp7CiAgICBwdWJsaWMgc3RhdGljIGJvb2wgVHJ5UGFyc2U8VD4oc3RyaW5nIHMsIG91dCBUIHJlc3VsdCkKICAgIHsKICAgICAgICByZXR1cm4gSW5uZXI8VD4ucGFyc2VyKHMsIG91dCByZXN1bHQpOwogICAgfQoKICAgIHB1YmxpYyBzdGF0aWMgVD8gUGFyc2VPck51bGw8VD4oc3RyaW5nIHMpCiAgICAgICAgd2hlcmUgVCA6IHN0cnVjdAogICAgewogICAgICAgIFQgcmVzdWx0OwogICAgICAgIGlmIChUcnlQYXJzZTxUPihzLCBvdXQgcmVzdWx0KSkgcmV0dXJuIHJlc3VsdDsKICAgICAgICBlbHNlIHJldHVybiBudWxsOwogICAgfQoKICAgIHN0YXRpYyBjbGFzcyBJbm5lcjxUPgogICAgewogICAgICAgIHB1YmxpYyBzdGF0aWMgVHJ5UGFyc2VyPFQ+IHBhcnNlcjsKCiAgICAgICAgc3RhdGljIElubmVyKCkKICAgICAgICB7CiAgICAgICAgICAgIHZhciBtID0gdHlwZW9mKFQpLkdldE1ldGhvZCgiVHJ5UGFyc2UiLCBuZXdbXSB7IHR5cGVvZihzdHJpbmcpLCB0eXBlb2YoVCkuTWFrZUJ5UmVmVHlwZSgpIH0pOwoKICAgICAgICAgICAgaWYgKG0gPT0gbnVsbCkKICAgICAgICAgICAgICAgIHRocm93IG5ldyBOb3RTdXBwb3J0ZWRFeGNlcHRpb24oKTsKCiAgICAgICAgICAgIHBhcnNlciA9IChUcnlQYXJzZXI8VD4pRGVsZWdhdGUuQ3JlYXRlRGVsZWdhdGUodHlwZW9mKFRyeVBhcnNlcjxUPiksIG0pOwogICAgICAgIH0KICAgIH0KfQoKY2xhc3MgUHJvZ3JhbQp7CiAgICBzdGF0aWMgdm9pZCBNYWluKCkKICAgIHsKICAgICAgICBDb25zb2xlLldyaXRlTGluZShQYXJzZXIuUGFyc2VPck51bGw8aW50PigiMTIzNCIpKTsKICAgICAgICBDb25zb2xlLldyaXRlTGluZShQYXJzZXIuUGFyc2VPck51bGw8aW50PigiMTJhMzQiKSk7CiAgICAgICAgQ29uc29sZS5Xcml0ZUxpbmUoUGFyc2VyLlBhcnNlT3JOdWxsPGludD4oIjEyMzQ0YXEiKSk7CiAgICAgICAgQ29uc29sZS5Xcml0ZUxpbmUoUGFyc2VyLlBhcnNlT3JOdWxsPGludD4oIjEyM3NhZnc0IikpOwogICAgICAgIENvbnNvbGUuV3JpdGVMaW5lKFBhcnNlci5QYXJzZU9yTnVsbDxkb3VibGU+KCIxLjIzNCIpKTsKICAgICAgICBDb25zb2xlLldyaXRlTGluZShQYXJzZXIuUGFyc2VPck51bGw8ZG91YmxlPigiMTIuMzQiKSk7CiAgICAgICAgQ29uc29sZS5Xcml0ZUxpbmUoUGFyc2VyLlBhcnNlT3JOdWxsPGRvdWJsZT4oIjEyLmEzNCIpKTsKCiAgICAgICAgRnVuYzxzdHJpbmcsIGJ5dGU/PiBwYXJzZXIgPSBQYXJzZXIuUGFyc2VPck51bGw8Ynl0ZT47CgogICAgICAgIENvbnNvbGUuV3JpdGVMaW5lKHBhcnNlcigiMjU1IikpOwogICAgfQp9Cg==