繁体   English   中英

通过运行并集和交集来组合5个sql查询的结果

[英]combining result of 5 sql queries by running a union and intersection

我有5个查询,如下所示,我需要对所有对象执行合并

  if($dv_state_ids!="")//check if no state is entered
    $state_sql="SELECT pkg_id FROM package_state where state_id in ($dv_state_ids)  ";
  if($dv_city_ids!="")//check if no city is entered
    $city_sql="SELECT pkg_id FROM package_city where  city_id in ($dv_city_ids)";
  if($dv_category_ids!="")//check if nocategory is entered
    $category_sql="SELECT pkg_id FROM package_category where category_id in ($dv_category_ids) ";
  if($dv_sub_category_ids!="")//check if no subcategory is found
    $sub_category_sql="SELECT pkg_id FROM package_category where subcategory_id in ($dv_sub_category_ids) ";
  if($dv_category_ids!="")
    $package_sql="SELECT pkg_id FROM package where id in ($dv_category_ids) ";

我可以通过以下语句对上述查询运行联合

$sql_get_any_packages=$state_sql." union ".$city_sql." 
union 
".$category_sql." union ".$sub_category_sql." union ".$package_sql ;

但是,如果任何查询为空,则将在mysql中生成错误。 一种方式是,我对32个条件进行构架(这将由这5个查询组成,以检查不同的条件)

有人能建议我另辟out径吗

我也需要对这5个查询的结果执行交集,而sql不支持INTERSECT

请在这件事上给予我帮助

“查询为null”显然意味着PHP变量为null 这绝不是特定于SQL或SQL联合的。

if s重复

因此,您可以执行以下操作:

$sql_get_any_packages = "";
if (!is_null($state_sql))
 $sql_get_any_packages .= " union " . $state_sql;
if (!is_null($city_sql))
 $sql_get_any_packages .= " union " . $city_sql;
if (!is_null($category_sql))
 $sql_get_any_packages .= " union " . $category_sql;
if (!is_null($sub_category_sql))
 $sql_get_any_packages .= " union " . $sub_category_sql;
if (!is_null($package_sql))
 $sql_get_any_packages .= " union " . $package_sql;
$sql_get_any_packages = substr($sql_get_any_packages, strlen(" union "));

这只是收集所有非null部分,包括每个部分的前导" union " ,并在末尾删除初始的" union " 如果所有查询可能同时为null ,则最终结果将为FALSE

使用数组

作为替代方案,你可以放下你的零件到一个数组,使用array_filternull元素,然后implode使用结果" union "胶水。 相应的代码可能如下所示(另请参见ideone上的示例 ):

$sql_get_any_packages = array(
    $state_sql,
    $city_sql,
    $category_sql,
    $sub_category_sql,
    $package_sql);
$sql_get_any_packages = array_filter($sql_get_any_packages);
$sql_get_any_packages = implode(" union ", $sql_get_any_packages);

关于相交

如果要结果相交 ,则不希望将其合并。 合并后,您将无法再访问其各个部分,因此无法将它们相互比较。 要实现交集,可以在SQL中使用联接 完整的示例如下所示:

SELECT package_state.pkg_id
FROM package_state, package_city, package_category, package_category, package
WHERE package_state.state_id IN ($dv_state_ids)
  AND package_city.city_id IN ($dv_city_ids)
  AND package_category.category_id IN ($dv_category_ids)
  AND package_category.subcategory_id IN ($dv_sub_category_ids)
  AND package.id in ($dv_category_ids)
  AND package_state.pkg_id == package_city.pkg_id
  AND package_state.pkg_id == package_category.pkg_id
  AND package_state.pkg_id == package.pkg_id

您可以使用如上所述的解决方案来构建这样的查询,但是它们将变得稍微复杂一些。 特别是,上述查询中的表package_state与所有其他表的作用有所不同:这是您SELECT输出值的表形式, s also the table which occurs on the left hand side of all the pkg_id comparisons, where the other tables appear on the right hand side. So you might want to collect several arrays, one of table names and one of s also the table which occurs on the left hand side of all the comparisons, where the other tables appear on the right hand side. So you might want to collect several arrays, one of table names and one of comparisons, where the other tables appear on the right hand side. So you might want to collect several arrays, one of table names and one of foo IN(bar)条件之一。 然后,您可以使用表名称数组的第一个元素扮演特殊角色。

当心SQL注入

注意将用户请求中的字符串粘贴到查询中。 它们可能包含丑陋的东西,会破坏您的数据。 确保输入是合理的,例如,通过检查它只是一个用逗号分隔的整数值列表来确保。 使用准备好的语句 ,可以使您远离大多数此类问题。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM