SQL使用Union All选择常量,然后使用IQueryable,EF加入

时间:2015-12-04 18:15:06

标签: c# entity-framework linq

使用EF 6

是否可以通过Linq生成以下SQL:

$connect = mysqli_connect('localhost', 'user', 'password','bachmanns_database') or die('errorerrorlolerror');
$url="";
if(isset($_POST['zipcode'])){
$zipcode = $_POST['zipcode'];
if($zipcode >= 0 && $zipcode <= 40000){
    $url = "pages/midwest.php";
}
}
?>

<div id="custom-search-input">
<div class="input-group col-md-12">
    <form method="post" action="<?php echo $url; ?>">
        <fieldset>
            <h3> Search your city: </h3>
            <input type="number" name="zipcode" id="zipcode" class="form-control input-lg" placeholder="ZIP Code..." min="0" max="50000">
            <input name="submit" id="submit" type="submit" value="Search" >
        </fieldset>
    </form>
</div>
</div>

调用Queryable.SelectMany在Unable上使用缺点,我将其定义为Array.AsQueryable(),因为该对象不是基元或枚举。有什么方法可以使用Queryable来绕过Enumerable,以便使用 select ... union all 构造来创建临时缺点表吗?也许扩展提供者?

1 个答案:

答案 0 :(得分:2)

两种方法。一个是将问题转移到头上并进行如下查询:

方法1:

SELECT *
FROM SomeEntity
WHERE sm.SomeProp >= [start1] and sm.SomeProp <= [end1]
UNION ALL
SELECT *
FROM SomeEntity
WHERE sm.SomeProp >= [start2] and sm.SomeProp <= [end2]
...
UNION ALL
SELECT *
FROM SomeEntity
WHERE sm.SomeProp >= [startx] and sm.SomeProp <= [endx]

方法2:

SELECT *
FROM SomeEntity
WHERE 1=0 /* Always false */
OR (sm.SomeProp >= [start1] and sm.SomeProp <= [end1])
OR (sm.SomeProp >= [start2] and sm.SomeProp <= [end2])
..
OR (sm.SomeProp >= [startx] and sm.SomeProp <= [endx])

LINQ中的方法1看起来像这样:

// Wrap in if(!array.Any()) if you want to handle the case where array is empty
var temp1=array.First(); // will throw exception if array is empty
var query=_db.SomeEntity.Where(s=>s.SomeProp>=temp1.start && s.SomeProp<=temp1.end));
foreach(var pair in array.Skip(1))
{
  var temp=pair;
  query=query.Union(
    _db.SomeEntity.Where(s=>s.SomeProp>=temp.start && s.SomeProp<=temp.end));
}

LINQ中的方法2可能会使用谓词构建器,如下所示:

var predicate = PredicateBuilder.False<SomeEntity>();
foreach (var pair in array)
{
  var temp=pair;
  predicate = predicate.Or(s=>s=>s.SomeProp>=temp.start && s.SomeProp<=temp.end));
}
var result=_db.SomeEntity.Where(predicate);