所以我需要基于4个不同的Id字段加入两个表。在第一个表中,需要3个ID,其中第4个是可选的。它们代表组织,部门,职位和可选单位,我将称之为opUnit。在第二个表中,我有4个不同的id字段都可以为空。它们用作对org / dep / pos / opUnit的特定组的赋值。如果这些字段中的任何一个为空,那么我们可以假设它在所有单元上匹配。例如,org id为3且dep id为24,后跟null pos和null opUnit id将意味着此特定赋值属于org中具有id 3和id为24的部门的所有位置。
那说我需要进行加入。
我最初看起来像这样的东西
from user in listOfUsers
join odp in this.DBContext.odpOpUnitTable on user.positionFieldId equals odp.userPositionFieldId //each user has an odp/opUnit, so join from users
from minReq in this.DBContext.ODPRequirementTable.Where(req => (!req.UseOrganization || odp.OrganizationId == req.OrganizationId)
&& (!req.UseDepartment || odp.DepartmentId == req.DepartmentId)
&& (!req.UsePosition || odp.PositionId == req.PositionId)
&& (!req.UseOpUnit || odp.OpUnitId == req.OpUnitId)).DefaultIfEmpty()
"使用___"字段只是辅助字段,表示相应的Id为空,不用于过滤org / dep / pos / opUnit。那句话做了我需要它做的事情,但它的速度慢得令人无法接受。我想做的是类似下面的
from user in listOfUsers
join odp in this.DBContext.odpOpUnitTable on user.positionFieldId equals odp.userPositionFieldId //each user has an odp/opUnit, so join from users
join minReq in this.DBContext.ODPRequirementTable on new { orgId = odp.OrganizationId, depId = odp.DepartmentId, posId = odp.PositionId, opId = odp.OpUnitId }
equals new { orgId = minReq.UseOrganization ? minReq.OrganizationId : odp.OrganizationId
depId = minReq.UseDepartment ? minReq.DepartmentId : odp.DepartmentId
posId = minReq.UsePosition ? minReq.PositionId : odp.PositionId
opId = minReq.UseOpUnit ? minReq.OpUnitId : odp.OpUnitId
}
基本上,只使用不为空的字段来执行连接。这个特定的例子不起作用,因为它使用右侧方程左侧的字段。
我的问题基本上列在here但是接受的解决方案是"使用where子句代替",但是where子句在我的情况下不起作用,因为需要多长时间。或者,有人提到在联接中对不同的OR情况使用联合,但这将是每个id为null的联合,这类似于16个联合或类似的东西,所以这也是不可接受的。
我不知道是否可以这样做,但我还没有找到这样的问题,所以希望这是一个有用的问题。
编辑:只是为了澄清我理解如何在SQL中执行此操作,但我想知道是否有LINQ方法可以在不牺牲性能的情况下执行此操作。