Linq To SQL 指定的强制转换对于 Union 无效错误

2024-03-25

我有以下代码,它在 .NET 4.0 中针对 SQL Server 2008 R2 服务器使用 Linq to SQL:

    public void Patients()
    {
        var documents = GetEMRDocumentsByPatientId("231966");
        if (documents.Count() > 0)
        {
            foreach (var doc in documents)
            {
                Console.WriteLine(doc.PatientId);
            }
        }
    }

    public static IQueryable<EMRDocument> GetEMRDocumentsByPatientId(string inPatientId)
    {
        return GetEMRDocuments().Where(d => String.Equals(d.PatientId, inPatientId));
    }

    public static IQueryable<EMRDocument> GetEMRDocuments()
    {
        var dataContext = InitializeDataContext();
        IQueryable<EMRDocument> retVal = null;

        retVal = (from e in dataContext.EMREvaluations
                  select new EMRDocument
                  {
                      PatientId = e.PatientId,
                      IsDeleted = e.Deleted,
                  }).Union(
                 from e2 in dataContext.EMRPatientDailyNotes
                 select new EMRDocument
                 {
                     PatientId = e2.PatientID,
                     IsDeleted = false,
                 });
        return retVal;
    }

应用程序的启动调用Patient();我第一次在 Patient() 的 foreach 行上收到 “对象引用未设置为对象的实例”“指定的转换无效”错误。documents.Count() 有效正确并从数据库中返回正确的记录数。我还可以获取文档生成的 SQL 并在 SSMS 中运行它,并且结果正确返回。

在运行的查询中,从 dataContext.EMRPatientDailyNotes 中进行的选择不会返回任何记录,因为该表中没有 PatientId 231966 的记录。

在 GetEMRDocuments() 中,如果我在两个选择中注释掉 IsDeleted = e.Deleted 和 IsDeleted = false,则下面的整个代码将执行而不会出现错误。如果我将 IsDeleted = e.Deleted 更改为 IsDeleted = false,则代码运行时不会出现错误。如果我删除整个联盟并运行 下列...

retVal = (from e in dataContext.EMREvaluations
          select new EMRDocument
          {
              PatientId = e.PatientId,
              IsDeleted = e.Deleted,
          });

...然后这段代码执行没有错误。另外,e.Deleted 是数据库中的 bool,而不是 bool?(nullable bool),而 IsDeleted 是 bool。以前有人见过此类问题吗?我不知道该怎么做才能解决这个问题。另外,我之前使用 Linq To Entities 进行相同的查询,但没有收到此错误。任何帮助将不胜感激。

谢谢, 担

EDIT:这是堆栈跟踪。我还有一些其他代码似乎隐藏了实际的错误:

[InvalidCastException: Specified cast is not valid.]
System.Data.SqlClient.SqlBuffer.get_Boolean() +5057281
System.Data.SqlClient.SqlDataReader.GetBoolean(Int32 i) +38
Read_EMRDocument(ObjectMaterializer`1 ) +313
System.Data.Linq.SqlClient.ObjectReader`2.MoveNext() +32
ATI.TherapyConnect.Service.Patients() in C:\SVN\Application\branches\dan.cagney\ATI.TherapyConnect\Service.asmx.cs:57
ATI.TherapyConnect.Content.UserControls.Shared.Patients.MyPatientsList.BindGrid(String inSortExpression, Int32 inCurrentPage) in C:\SVN\Application\branches\dan.cagney\ATI.TherapyConnect\Content\UserControls\Shared\Patients\MyPatientsList.ascx.cs:129
ATI.TherapyConnect.Content.UserControls.Shared.Patients.MyPatientsList.Page_Load(Object sender, EventArgs e) in C:\SVN\Application\branches\dan.cagney\ATI.TherapyConnect\Content\UserControls\Shared\Patients\MyPatientsList.ascx.cs:68
System.Web.Util.CalliHelper.EventArgFunctionCaller(IntPtr fp, Object o, Object t, EventArgs e) +14
System.Web.Util.CalliEventHandlerDelegateProxy.Callback(Object sender, EventArgs e) +35
System.Web.UI.Control.OnLoad(EventArgs e) +91
System.Web.UI.Control.LoadRecursive() +74
System.Web.UI.Control.LoadRecursive() +146
System.Web.UI.Control.LoadRecursive() +146
System.Web.UI.Control.LoadRecursive() +146
System.Web.UI.Control.LoadRecursive() +146
System.Web.UI.Page.ProcessRequestMain(Boolean includeStagesBeforeAsyncPoint, Boolean includeStagesAfterAsyncPoint) +2207

因此,显然 IsDeleted 的 bool 值存在转换问题。由于 dataContext.EMRPatientDailyNotes 没有返回结果,它是否会尝试将 null 值映射到 Union 的 IsDeleted 中?我不认为这会是问题,因为如果我只是将 IsDeleted = e.Deleted 更改为 IsDeleted = false,就不会出现错误。因此,看起来 e.Deleted 返回的是非布尔值。但是,当 e.Deleted 被定义为 Linq To SQL 生成代码中的 bool 并且它是 SQL 数据库中的一个位字段而不是 null 字段时,这怎么可能呢?


我终于能够让它发挥作用,但我不知道为什么需要我的改变。这是我将查询更改为:

retVal = (from e in dataContext.EMREvaluations 
              select new EMRDocument 
              { 
                  PatientId = e.PatientId, 
                  IsDeleted = e.Deleted == null ? false : e.Deleted, 
              }).Union( 
             from e2 in dataContext.EMRPatientDailyNotes 
             select new EMRDocument 
             { 
                 PatientId = e2.PatientID, 
                 IsDeleted = false, 
             }); 

我修改了

IsDeleted = e.Deleted 

to

IsDeleted = e.Deleted == null ? false : e.Deleted

但是我不知道为什么需要这样做,因为 e.Deleted 在数据库中被列为 bool (非空),那么 e.Deleted 怎么可能有 null 值?我现在将其标记为答案,但是如果有人可以告诉我为什么需要此代码更改,或者我如何在不更改代码的情况下完成此操作,我会将其标记为答案。

谢谢, 担

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

Linq To SQL 指定的强制转换对于 Union 无效错误 的相关文章

随机推荐