我正在开发代码生成器并尝试将 CLR 类型映射到 SQL 类型。
示例:
using System.Data;
using System.Data.SqlTypes;
var dictionaryCtsToSql = new Dictionary<Type, SqlDbType>();
dictionaryCtsToSql.Add(typeof(Boolean), SqlDbType.Bit);
dictionaryCtsToSql.Add(typeof(Boolean?), SqlDbType.Bit);
...
dictionaryCtsToSql.Add(typeof(Byte), SqlDbType.TinyInt);
dictionaryCtsToSql.Add(typeof(Byte?), SqlDbType.TinyInt);
dictionaryCtsToSql.Add(typeof(Int32), SqlDbType.Int);
dictionaryCtsToSql.Add(typeof(Int32?), SqlDbType.Int);
dictionaryCtsToSql.Add(typeof(UInt32), SqlDbType.BigInt);
dictionaryCtsToSql.Add(typeof(UInt32?), SqlDbType.BigInt);
dictionaryCtsToSql.Add(typeof(Single), SqlDbType.Real);
dictionaryCtsToSql.Add(typeof(Single?), SqlDbType.Real);
...
dictionaryCtsToSql.Add(typeof(DateTime), SqlDbType.DateTime2);
dictionaryCtsToSql.Add(typeof(DateTime?), SqlDbType.DateTime2);
dictionaryCtsToSql.Add(typeof(DateTimeOffset), SqlDbType.DateTimeOffset);
dictionaryCtsToSql.Add(typeof(DateTimeOffset?), SqlDbType.DateTimeOffset);
...
这适用于基元/值类型,但不适用于可空字符串,如下所示:
dictionaryCtsToSql.Add(typeof(String), SqlDbType.NVarChar);
dictionaryCtsToSql.Add(typeof(String?), SqlDbType.NVarChar); // Error.
现在,我完全理解为什么这会导致引用类型出现错误,但我的目标是使用 C# 12 的 .NET 8,并且该项目已启用其可空性设置:
<PropertyGroup>
<TargetFramework>net8.0</TargetFramework>
<Nullable>enable</Nullable>
</PropertyGroup>
因此,考虑以下课程:
using System.Data;
using System.Data.SqlTypes;
public class Entity
{
public long Id { get; set; }
public string NameGiven { get; set; } = string.Empty;
public string? NameMiddle { get; set; }
public string NameFamily { get; set; } = string.Empty;
public DateTime DateTimeFrom { get; set; } = SqlDateTime.MinValue.Value;
public DateTime? DateTimeUntil { get; set; }
}
我检查了反射属性,看起来
Type
仍然是 String
,并添加了 NullableAttribute
:
另一方面,值类型被包装在另一个结构体
Nullable<TValueType>
中。这意味着 string?
与 int?
不同,根本不是一种新类型。
因此,反对这种冗长解释的问题是:如果可能的话,我非常想使用现有的字典
Dictionary<Type, SqlDbType>
,而不必检查代码中的可为空属性。这可能吗?如果不是的话,不是应该吗?
我想我有点难过知道可空引用类型似乎是为了代码质量而不是运行时功能而设计的。
“我想我有点难过知道可空引用类型似乎是为了代码质量而不是运行时功能而设计的” - 令你失望的是,这是真的。