Add DateTime{Offset} span-based {Try}Parse{Exact} overloads
authorStephen Toub <stoub@microsoft.com>
Thu, 5 Oct 2017 21:47:49 +0000 (17:47 -0400)
committerStephen Toub <stoub@microsoft.com>
Fri, 6 Oct 2017 12:27:44 +0000 (08:27 -0400)
src/mscorlib/shared/System/DateTime.cs
src/mscorlib/shared/System/DateTimeOffset.cs
src/mscorlib/shared/System/Globalization/DateTimeFormatInfo.cs

index dec2e6e..27c9fda 100644 (file)
@@ -1111,6 +1111,12 @@ namespace System
             return (DateTimeParse.Parse(s.AsReadOnlySpan(), DateTimeFormatInfo.GetInstance(provider), styles));
         }
 
+        public static DateTime Parse(ReadOnlySpan<char> s, IFormatProvider provider = null, DateTimeStyles styles = DateTimeStyles.None)
+        {
+            DateTimeFormatInfo.ValidateStyles(styles, nameof(styles));
+            return DateTimeParse.Parse(s, DateTimeFormatInfo.GetInstance(provider), styles);
+        }
+
         // Constructs a DateTime from a string. The string must specify a
         // date and optionally a time in a culture-specific or universal format.
         // Leading and trailing whitespace characters are allowed.
@@ -1132,6 +1138,12 @@ namespace System
             return (DateTimeParse.ParseExact(s.AsReadOnlySpan(), format, DateTimeFormatInfo.GetInstance(provider), style));
         }
 
+        public static DateTime ParseExact(ReadOnlySpan<char> s, string format, IFormatProvider provider, DateTimeStyles style = DateTimeStyles.None)
+        {
+            DateTimeFormatInfo.ValidateStyles(style, nameof(style));
+            return DateTimeParse.ParseExact(s, format, DateTimeFormatInfo.GetInstance(provider), style);
+        }
+
         public static DateTime ParseExact(String s, String[] formats, IFormatProvider provider, DateTimeStyles style)
         {
             DateTimeFormatInfo.ValidateStyles(style, nameof(style));
@@ -1139,6 +1151,12 @@ namespace System
             return DateTimeParse.ParseExactMultiple(s.AsReadOnlySpan(), formats, DateTimeFormatInfo.GetInstance(provider), style);
         }
 
+        public static DateTime ParseExact(ReadOnlySpan<char> s, string[] formats, IFormatProvider provider, DateTimeStyles style = DateTimeStyles.None)
+        {
+            DateTimeFormatInfo.ValidateStyles(style, nameof(style));
+            return DateTimeParse.ParseExactMultiple(s, formats, DateTimeFormatInfo.GetInstance(provider), style);
+        }
+
         public TimeSpan Subtract(DateTime value)
         {
             return new TimeSpan(InternalTicks - value.InternalTicks);
@@ -1287,6 +1305,11 @@ namespace System
             return DateTimeParse.TryParse(s.AsReadOnlySpan(), DateTimeFormatInfo.CurrentInfo, DateTimeStyles.None, out result);
         }
 
+        public static bool TryParse(ReadOnlySpan<char> s, out DateTime result)
+        {
+            return DateTimeParse.TryParse(s, DateTimeFormatInfo.CurrentInfo, DateTimeStyles.None, out result);
+        }
+
         public static Boolean TryParse(String s, IFormatProvider provider, DateTimeStyles styles, out DateTime result)
         {
             DateTimeFormatInfo.ValidateStyles(styles, nameof(styles));
@@ -1300,6 +1323,12 @@ namespace System
             return DateTimeParse.TryParse(s.AsReadOnlySpan(), DateTimeFormatInfo.GetInstance(provider), styles, out result);
         }
 
+        public static bool TryParse(ReadOnlySpan<char> s, IFormatProvider provider, DateTimeStyles styles, out DateTime result)
+        {
+            DateTimeFormatInfo.ValidateStyles(styles, nameof(styles));
+            return DateTimeParse.TryParse(s, DateTimeFormatInfo.GetInstance(provider), styles, out result);
+        }
+
         public static Boolean TryParseExact(String s, String format, IFormatProvider provider, DateTimeStyles style, out DateTime result)
         {
             DateTimeFormatInfo.ValidateStyles(style, nameof(style));
@@ -1313,6 +1342,12 @@ namespace System
             return DateTimeParse.TryParseExact(s.AsReadOnlySpan(), format, DateTimeFormatInfo.GetInstance(provider), style, out result);
         }
 
+        public static bool TryParseExact(ReadOnlySpan<char> s, string format, IFormatProvider provider, DateTimeStyles style, out DateTime result)
+        {
+            DateTimeFormatInfo.ValidateStyles(style, nameof(style));
+            return DateTimeParse.TryParseExact(s, format, DateTimeFormatInfo.GetInstance(provider), style, out result);
+        }
+
         public static Boolean TryParseExact(String s, String[] formats, IFormatProvider provider, DateTimeStyles style, out DateTime result)
         {
             DateTimeFormatInfo.ValidateStyles(style, nameof(style));
@@ -1326,6 +1361,12 @@ namespace System
             return DateTimeParse.TryParseExactMultiple(s.AsReadOnlySpan(), formats, DateTimeFormatInfo.GetInstance(provider), style, out result);
         }
 
+        public static bool TryParseExact(ReadOnlySpan<char> s, string[] formats, IFormatProvider provider, DateTimeStyles style, out DateTime result)
+        {
+            DateTimeFormatInfo.ValidateStyles(style, nameof(style));
+            return DateTimeParse.TryParseExactMultiple(s, formats, DateTimeFormatInfo.GetInstance(provider), style, out result);
+        }
+
         public static DateTime operator +(DateTime d, TimeSpan t)
         {
             long ticks = d.InternalTicks;
index 1373039..3855dc5 100644 (file)
@@ -632,6 +632,13 @@ namespace System
             return new DateTimeOffset(dateResult.Ticks, offset);
         }
 
+        public static DateTimeOffset Parse(ReadOnlySpan<char> input, IFormatProvider formatProvider = null, DateTimeStyles styles = DateTimeStyles.None)
+        {
+            styles = ValidateStyles(styles, nameof(styles));
+            DateTime dateResult = DateTimeParse.Parse(input, DateTimeFormatInfo.GetInstance(formatProvider), styles, out TimeSpan offset);
+            return new DateTimeOffset(dateResult.Ticks, offset);
+        }
+
         // Constructs a DateTimeOffset from a string. The string must specify a
         // date and optionally a time in a culture-specific or universal format.
         // Leading and trailing whitespace characters are allowed.
@@ -660,6 +667,13 @@ namespace System
             return new DateTimeOffset(dateResult.Ticks, offset);
         }
 
+        public static DateTimeOffset ParseExact(ReadOnlySpan<char> input, string format, IFormatProvider formatProvider, DateTimeStyles styles = DateTimeStyles.None)
+        {
+            styles = ValidateStyles(styles, nameof(styles));
+            DateTime dateResult = DateTimeParse.ParseExact(input, format, DateTimeFormatInfo.GetInstance(formatProvider), styles, out TimeSpan offset);
+            return new DateTimeOffset(dateResult.Ticks, offset);
+        }
+
         public static DateTimeOffset ParseExact(String input, String[] formats, IFormatProvider formatProvider, DateTimeStyles styles)
         {
             styles = ValidateStyles(styles, nameof(styles));
@@ -674,6 +688,13 @@ namespace System
             return new DateTimeOffset(dateResult.Ticks, offset);
         }
 
+        public static DateTimeOffset ParseExact(ReadOnlySpan<char> input, string[] formats, IFormatProvider formatProvider, DateTimeStyles styles = DateTimeStyles.None)
+        {
+            styles = ValidateStyles(styles, nameof(styles));
+            DateTime dateResult = DateTimeParse.ParseExactMultiple(input, formats, DateTimeFormatInfo.GetInstance(formatProvider), styles, out TimeSpan offset);
+            return new DateTimeOffset(dateResult.Ticks, offset);
+        }
+
         public TimeSpan Subtract(DateTimeOffset value)
         {
             return UtcDateTime.Subtract(value.UtcDateTime);
@@ -768,6 +789,13 @@ namespace System
             return parsed;
         }
 
+        public static bool TryParse(ReadOnlySpan<char> input, out DateTimeOffset result)
+        {
+            bool parsed = DateTimeParse.TryParse(input, DateTimeFormatInfo.CurrentInfo, DateTimeStyles.None, out DateTime dateResult, out TimeSpan offset);
+            result = new DateTimeOffset(dateResult.Ticks, offset);
+            return parsed;
+        }
+
         public static Boolean TryParse(String input, IFormatProvider formatProvider, DateTimeStyles styles, out DateTimeOffset result)
         {
             styles = ValidateStyles(styles, nameof(styles));
@@ -788,6 +816,14 @@ namespace System
             return parsed;
         }
 
+        public static bool TryParse(ReadOnlySpan<char> input, IFormatProvider formatProvider, DateTimeStyles styles, out DateTimeOffset result)
+        {
+            styles = ValidateStyles(styles, nameof(styles));
+            bool parsed = DateTimeParse.TryParse(input, DateTimeFormatInfo.GetInstance(formatProvider), styles, out DateTime dateResult, out TimeSpan offset);
+            result = new DateTimeOffset(dateResult.Ticks, offset);
+            return parsed;
+        }
+
         public static Boolean TryParseExact(String input, String format, IFormatProvider formatProvider, DateTimeStyles styles,
                                             out DateTimeOffset result)
         {
@@ -810,6 +846,15 @@ namespace System
             return parsed;
         }
 
+        public static bool TryParseExact(
+            ReadOnlySpan<char> input, string format, IFormatProvider formatProvider, DateTimeStyles styles, out DateTimeOffset result)
+        {
+            styles = ValidateStyles(styles, nameof(styles));
+            bool parsed = DateTimeParse.TryParseExact(input, format, DateTimeFormatInfo.GetInstance(formatProvider), styles, out DateTime dateResult, out TimeSpan offset);
+            result = new DateTimeOffset(dateResult.Ticks, offset);
+            return parsed;
+        }
+
         public static Boolean TryParseExact(String input, String[] formats, IFormatProvider formatProvider, DateTimeStyles styles,
                                             out DateTimeOffset result)
         {
@@ -832,6 +877,15 @@ namespace System
             return parsed;
         }
 
+        public static bool TryParseExact(
+            ReadOnlySpan<char> input, string[] formats, IFormatProvider formatProvider, DateTimeStyles styles, out DateTimeOffset result)
+        {
+            styles = ValidateStyles(styles, nameof(styles));
+            bool parsed = DateTimeParse.TryParseExactMultiple(input, formats, DateTimeFormatInfo.GetInstance(formatProvider), styles, out DateTime dateResult, out TimeSpan offset);
+            result = new DateTimeOffset(dateResult.Ticks, offset);
+            return parsed;
+        }
+
         // Ensures the TimeSpan is valid to go in a DateTimeOffset.
         private static Int16 ValidateOffset(TimeSpan offset)
         {
index de26079..297b556 100644 (file)
@@ -454,35 +454,12 @@ namespace System.Globalization
             }
         }
 
-
-        public static DateTimeFormatInfo GetInstance(IFormatProvider provider)
-        {
-            // Fast case for a regular CultureInfo
-            DateTimeFormatInfo info;
-            CultureInfo cultureProvider = provider as CultureInfo;
-            if (cultureProvider != null && !cultureProvider._isInherited)
-            {
-                return cultureProvider.DateTimeFormat;
-            }
-            // Fast case for a DTFI;
-            info = provider as DateTimeFormatInfo;
-            if (info != null)
-            {
-                return info;
-            }
-            // Wasn't cultureInfo or DTFI, do it the slower way
-            if (provider != null)
-            {
-                info = provider.GetFormat(typeof(DateTimeFormatInfo)) as DateTimeFormatInfo;
-                if (info != null)
-                {
-                    return info;
-                }
-            }
-            // Couldn't get anything, just use currentInfo as fallback
-            return CurrentInfo;
-        }
-
+        public static DateTimeFormatInfo GetInstance(IFormatProvider provider) =>
+            provider == null ? CurrentInfo :
+            provider is CultureInfo cultureProvider && !cultureProvider._isInherited ? cultureProvider.DateTimeFormat :
+            provider is DateTimeFormatInfo info ? info :
+            provider.GetFormat(typeof(DateTimeFormatInfo)) is DateTimeFormatInfo info2 ? info2 :
+            CurrentInfo; // Couldn't get anything, just use currentInfo as fallback
 
         public Object GetFormat(Type formatType)
         {