Oracle Data Provider to CLR type mapping

99封情书 提交于 2019-12-04 14:42:54

Run this simple test to get mappings for SqlServer and Oracle (both MS and ODP.NET drivers):

using System;
using System.Collections.Generic;
using System.Data;
using System.Data.SqlClient;
using System.Linq;
using Oracle.DataAccess.Client;

namespace DbOutTypeTest
{
    public class Program
    {
        private static string SqlServerConnectionString = @"";
        private static string OracleConnectionString = @"";

        private static void WriteHeader(string title)
        {
            Console.WriteLine("----------------------------------------------------------");
            Console.WriteLine("-- {0}", title);
            Console.WriteLine("----------------------------------------------------------");
        }

        private static void WriteRow(string key, string value)
        {
            Console.WriteLine("{0}\t\t{1}", key.PadRight(30, ' '), value);
        }

        private static void EnumerateTypes(IDbConnection connection, string template, IEnumerable<string> types)
        {
            EnumerateTypes(connection, template, types, (arg1, arg2) => { });
        }

        private static void EnumerateTypes(IDbConnection connection, string template, IEnumerable<string> types, Action<string, string> action)
        {
            connection.Open();
            using (var command = connection.CreateCommand())
            {
                foreach (var type in types)
                {
                    var value = "";
                    command.CommandText = string.Format(template, type);
                    try
                    {
                        using (var reader = command.ExecuteReader())
                        {
                            if (reader.Read())
                                value = reader[0].GetType().FullName;
                            else
                                value = "<no data read>";
                        }
                    }
                    catch (Exception ex)
                    {
                        value = ex.Message;
                    }
                    WriteRow(type, value);
                    action(type, value);
                }
            }
        }

        private static IEnumerable<string> SqlServerIntegers()
        {
            yield return "tinyint";
            yield return "smallint";
            yield return "int";
            yield return "bigint";
            for (int precision = 1; precision <= 38; ++precision)
            {
                yield return "numeric(" + precision + ", 0)";
            }
            yield break;
        }

        private static IEnumerable<string> SqlServerFloatings()
        {
            yield return "real";
            yield return "float";
            for (int precision = 1; precision <= 38; ++precision)
            {
                for (int scale = 1; scale <= precision; ++scale)
                    yield return "numeric(" + precision + ", " + scale + ")";
            }
            yield break;
        }

        private static IEnumerable<string> OracleIntegers()
        {
            for (int precision = 1; precision <= 38; ++precision)
            {
                yield return "number(" + precision + ", 0)";
            }
            yield break;
        }

        private static IEnumerable<string> OracleFloatings()
        {
            for (int precision = 1; precision <= 38; ++precision)
            {
                for (int scale = 1; scale <= precision; ++scale)
                    yield return "number(" + precision + ", " + scale + ")";
            }
            yield break;
        }

        public static void Main(string[] args)
        {
            WriteHeader("C# types - CLR names");
            Console.WriteLine("{0}\t\t{1}",   "byte".PadRight(30, ' '), typeof(byte).FullName);
            Console.WriteLine("{0}\t\t{1}",  "short".PadRight(30, ' '), typeof(short).FullName);
            Console.WriteLine("{0}\t\t{1}",    "int".PadRight(30, ' '), typeof(int).FullName);
            Console.WriteLine("{0}\t\t{1}",   "long".PadRight(30, ' '), typeof(long).FullName);
            Console.WriteLine("{0}\t\t{1}",  "float".PadRight(30, ' '), typeof(float).FullName);
            Console.WriteLine("{0}\t\t{1}", "double".PadRight(30, ' '), typeof(double).FullName);

            var OracleToClrInteger = new Dictionary<string, string>();
            var OracleToClrFloating = new Dictionary<string, string>();
            var SqlServerToClrInteger = new Dictionary<string, string>();
            var SqlServerToClrFloating = new Dictionary<string, string>();

            WriteHeader("Oracle integers mapping (Oracle Data Provider)");
            using (var connection = new OracleConnection(OracleConnectionString))
            {
                EnumerateTypes(connection, "SELECT CAST(0 AS {0}) FROM DUAL", OracleIntegers(), (type, value) => OracleToClrInteger.Add(type, value));
            }

            WriteHeader("SQLServer integers mapping");
            using (var connection = new SqlConnection(SqlServerConnectionString))
            {
                EnumerateTypes(connection, "SELECT CAST(0 AS {0})", SqlServerIntegers(), (type, value) => SqlServerToClrInteger.Add(type, value));
            }

            WriteHeader("Oracle integers mapping (Microsoft Oracle Client)");
            using (var connection = new System.Data.OracleClient.OracleConnection(OracleConnectionString))
            {
                EnumerateTypes(connection, "SELECT CAST(0 AS {0}) FROM DUAL", OracleIntegers());
            } 

            WriteHeader("Oracle floats mapping (Oracle Data Provider)");
            using (var connection = new OracleConnection(OracleConnectionString))
            {
                EnumerateTypes(connection, "SELECT CAST(0 AS {0}) FROM DUAL", OracleFloatings(), (type, value) => OracleToClrFloating.Add(type, value));
            }

            WriteHeader("SQLServer floats mapping");
            using (var connection = new SqlConnection(SqlServerConnectionString))
            {
                EnumerateTypes(connection, "SELECT CAST(0 AS {0})", SqlServerFloatings(), (type, value) => SqlServerToClrFloating.Add(type, value));
            }

            WriteHeader("Oracle floats mapping (Microsoft Oracle Client)");
            using (var connection = new System.Data.OracleClient.OracleConnection(OracleConnectionString))
            {
                EnumerateTypes(connection, "SELECT CAST(0 AS {0}) FROM DUAL", OracleFloatings());
            }

            WriteHeader("Suggested integer type mapping Oracle -> SqlServer");
            foreach (var pair in OracleToClrInteger)
            {
                if (pair.Value == "System.Decimal")
                    WriteRow(pair.Key, pair.Key.Replace("number", "numeric"));
                else
                {
                    if (!SqlServerToClrInteger.Values.Contains(pair.Value))
                        WriteRow(pair.Key, "???");
                    else
                        WriteRow(pair.Key, SqlServerToClrInteger.First(p => p.Value == pair.Value).Key);
                }
            }

            WriteHeader("Suggested floating type mapping Oracle -> SqlServer");
            foreach (var pair in OracleToClrFloating)
            {
                if (pair.Value == "System.Decimal")
                    WriteRow(pair.Key, pair.Key.Replace("number", "numeric"));
                else
                {
                    if (!SqlServerToClrFloating.Values.Contains(pair.Value))
                        WriteRow(pair.Key, "???");
                    else
                        WriteRow(pair.Key, SqlServerToClrFloating.First(p => p.Value == pair.Value).Key);
                }
            }

        }
    }
}

The most interesting part:

----------------------------------------------------------
-- Oracle integers mapping (Oracle Data Provider)
----------------------------------------------------------
number(1, 0)                        System.Int16
number(2, 0)                        System.Int16
number(3, 0)                        System.Int16
number(4, 0)                        System.Int16
number(5, 0)                        System.Int32
number(6, 0)                        System.Int32
number(7, 0)                        System.Int32
number(8, 0)                        System.Int32
number(9, 0)                        System.Int32
number(10, 0)                       System.Int64
number(11, 0)                       System.Int64
number(12, 0)                       System.Int64
number(13, 0)                       System.Int64
number(14, 0)                       System.Int64
number(15, 0)                       System.Int64
number(16, 0)                       System.Int64
number(17, 0)                       System.Int64
number(18, 0)                       System.Int64
number(19, 0)                       System.Decimal
number(20, 0)                       System.Decimal
number(21, 0)                       System.Decimal
number(22, 0)                       System.Decimal
number(23, 0)                       System.Decimal
number(24, 0)                       System.Decimal

Stefan, I had the same question myself.

You may find the answer here, in the installed DevArt DotConnect for Oracle Help documentation: ms-help://Devart.Data.Oracle/dcOracle/DataTypeMapping.html

You may want to browse online, in DevArt's website to find the same info: http://www.devart.com/dotconnect/oracle/docs/DataTypeMapping.html

Both are under the chapter entitled, "Entity Framework Data Type Mapping".

"Oracle to .NET type mapping - Type mapping rules from this table are used when generating a model from a database with Entity Data Model Wizard in Visual Studio 2008/2010 and Database Reverse Engineering Wizard in Entity Developer...."

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!