[hyena] [Hyena.Data.Sqlite] Improve data type casting



commit 896f326d5857f056be9a34ca72583a858066d66c
Author: Gabriel Burt <gabriel burt gmail com>
Date:   Wed Nov 17 11:50:17 2010 -0600

    [Hyena.Data.Sqlite] Improve data type casting
    
    Avoid Convert.ChangeType and Convert.To* to avoid CurrentCulture, and
    cache which types are enums because profiling shows that to be expensive
    as well.

 .../Hyena.Data.Sqlite/HyenaSqliteConnection.cs     |    6 ++--
 Hyena.Data.Sqlite/Hyena.Data.Sqlite/Sqlite.cs      |    2 +
 Hyena.Data.Sqlite/Hyena.Data.Sqlite/SqliteUtils.cs |   29 +++++++++++++-------
 3 files changed, 24 insertions(+), 13 deletions(-)
---
diff --git a/Hyena.Data.Sqlite/Hyena.Data.Sqlite/HyenaSqliteConnection.cs b/Hyena.Data.Sqlite/Hyena.Data.Sqlite/HyenaSqliteConnection.cs
index 3bf1fa3..a87e513 100644
--- a/Hyena.Data.Sqlite/Hyena.Data.Sqlite/HyenaSqliteConnection.cs
+++ b/Hyena.Data.Sqlite/Hyena.Data.Sqlite/HyenaSqliteConnection.cs
@@ -52,7 +52,7 @@ namespace Hyena.Data.Sqlite
             if (!read) {
                 Read ();
             }
-            return (T) SqliteUtils.FromDbFormat (typeof(T), reader[i]);
+            return reader.Get<T> (i);
         }
 
         public bool Read ()
@@ -162,7 +162,7 @@ namespace Hyena.Data.Sqlite
             Type type = typeof (T);
             using (IDataReader reader = Query (command)) {
                 while (reader.Read ()) {
-                    yield return (T) SqliteUtils.FromDbFormat (type, reader[0]);
+                    yield return (T) reader.Get (0, type);
                 }
             }
         }
@@ -172,7 +172,7 @@ namespace Hyena.Data.Sqlite
             Type type = typeof (T);
             using (IDataReader reader = Query (command, param_values)) {
                 while (reader.Read ()) {
-                    yield return (T) SqliteUtils.FromDbFormat (type, reader[0]);
+                    yield return (T) reader.Get (0, type);
                 }
             }
         }
diff --git a/Hyena.Data.Sqlite/Hyena.Data.Sqlite/Sqlite.cs b/Hyena.Data.Sqlite/Hyena.Data.Sqlite/Sqlite.cs
index de5fad0..9bbb0d2 100644
--- a/Hyena.Data.Sqlite/Hyena.Data.Sqlite/Sqlite.cs
+++ b/Hyena.Data.Sqlite/Hyena.Data.Sqlite/Sqlite.cs
@@ -493,6 +493,8 @@ namespace Hyena.Data.Sqlite
 
             if (o == null)
                 o = null;
+            else if (type == typeof(int))
+                o = (int)(long)o;
             else if (type == typeof(uint))
                 o = (uint)(long)o;
             else if (type == typeof(ulong))
diff --git a/Hyena.Data.Sqlite/Hyena.Data.Sqlite/SqliteUtils.cs b/Hyena.Data.Sqlite/Hyena.Data.Sqlite/SqliteUtils.cs
index eb56ec2..3f3ebe9 100644
--- a/Hyena.Data.Sqlite/Hyena.Data.Sqlite/SqliteUtils.cs
+++ b/Hyena.Data.Sqlite/Hyena.Data.Sqlite/SqliteUtils.cs
@@ -80,10 +80,13 @@ namespace Hyena.Data.Sqlite
                 return TimeSpan.MinValue.Equals ((TimeSpan)value)
                     ? (object)null
                     : ((TimeSpan)value).TotalMilliseconds;
-            } else if (type.IsEnum) {
-                return Convert.ChangeType (value, Enum.GetUnderlyingType (type));
             } else if (type == typeof (bool)) {
                 return ((bool)value) ? 1 : 0;
+            } else if (enum_types.Contains (type)) {
+                return Convert.ChangeType (value, Enum.GetUnderlyingType (type));
+            } else if (type.IsEnum) {
+                enum_types.Add (type);
+                return Convert.ChangeType (value, Enum.GetUnderlyingType (type));
             }
 
             return value;
@@ -101,21 +104,23 @@ namespace Hyena.Data.Sqlite
                 value = null;
 
             if (type == typeof (DateTime)) {
-                return value == null
-                    ? DateTime.MinValue
-                    : DateTimeUtil.ToDateTime (Convert.ToInt64 (value));
+                if (value == null)
+                    return DateTime.MinValue;
+                else if (!(value is long))
+                    value = Convert.ToInt64 (value);
+                return DateTimeUtil.ToDateTime ((long)value);
             } else if (type == typeof (TimeSpan)) {
-                return value == null
-                    ? TimeSpan.MinValue
-                    : TimeSpan.FromMilliseconds (Convert.ToInt64 (value));
+                if (value == null)
+                    return TimeSpan.MinValue;
+                else if (!(value is long))
+                    value = Convert.ToInt64 (value);
+                return TimeSpan.FromMilliseconds ((long)value);
             } else if (value == null) {
                 if (type.IsValueType) {
                     return Activator.CreateInstance (type);
                 } else {
                     return null;
                 }
-            } else if (type.IsEnum) {
-                return Enum.ToObject (type, value);
             } else if (type == typeof (bool)) {
                 return ((long)value == 1);
             } else if (type == typeof (double?)) {
@@ -124,6 +129,8 @@ namespace Hyena.Data.Sqlite
 
                 double double_value = ((Single?) value).Value;
                 return (double?) double_value;
+            } else if (type.IsEnum) {
+                return Enum.ToObject (type, value);
             } else {
                 return Convert.ChangeType (value, type);
             }
@@ -151,6 +158,8 @@ namespace Hyena.Data.Sqlite
             }
             return builder.ToString ();
         }
+
+        static HashSet<Type> enum_types = new HashSet<Type> ();
     }
 
     [SqliteFunction (Name = "HYENA_BINARY_FUNCTION", FuncType = FunctionType.Scalar, Arguments = 3)]



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]