跨表2是动态的2个数据库的mysql UNION?

时间:2016-09-14 21:56:08

标签: php mysql arrays

我有一系列MySQL联合,如下所示:

$stmt=$db->prepare('SELECT * FROM social_posts WHERE username IN (
                    SELECT friend2 as username FROM list_friends 
                    WHERE (friend1 = :username AND friend2 <> :username) 
                        UNION
                    SELECT friend1 as username FROM list_friends
                    WHERE (friend2 = :username AND friend1 <> :username)
                   )');
$stmt->bindParam(':username', $username);
$stmt->execute();
$row = $stmt->fetchAll();

我需要将类似的联合应用于第二个数据库中的动态表。我对该数据库/表的当前SELECT语句如下所示。

if ($db2->query("SHOW TABLES LIKE 'elfinder_file_".strtolower(:username)."'"
           )->rowCount() > 0 ){
    $stmt=$db2->prepare("SELECT * FROM elfinder_file_".strtolower(:username)." 
                         WHERE mime <> 'directory' GROUP BY time");
    $stmt->execute();
    $row4 = $stmt->fetchAll();
}

我遇到的问题是第一部分的UNION正在根据$ username的朋友选择数据,我不知道如何将这样的东西应用到代码的第二部分。

如何将 $ username 的朋友传递给SHOW TABLES语句和SELECT语句的动态表 strtolower(:username)

备注: 我不能使用foreach循环来获取朋友,然后通过第二个表循环它们。这样做的原因是其他表的结果与此表的结果不匹配。我也不能使用一个巨大的循环来获取朋友并将它们循环遍历每个表,因为然后循环的每个实例都覆盖了循环的最后一个实例并且我将循环的结果作为循环外的数组回显。每个循环实例的数组都不同。

2 个答案:

答案 0 :(得分:1)

你应该能够通过循环来完成它。我将所有结果都放在一个二维数组中;第一个维度是朋友名称,其值是相应表格中的行。

$stmt = $db->prepare("SELECT friend2 as username FROM list_friends 
                WHERE (friend1 = :username AND friend2 <> :username) 
                    UNION
                SELECT friend1 as username FROM list_friends
                WHERE (friend2 = :username AND friend1 <> :username)";
$stmt->bindParam(':username', $username);
$stmt->execute();
$friend_rows = $stmt->fetchAll();
$all_results = array();
foreach ($friend_rows as $row) {
    $friend = strtolower($row['username']);
    if ($db2->query("SHOW TABLES LIKE 'elfinder_file_$friend'"
               )->rowCount() > 0 ){
        $stmt=$db2->prepare("SELECT * FROM elfinder_file_$friend 
                             WHERE mime <> 'directory' GROUP BY time");
        $stmt->execute();
        $all_results[$friend] = $stmt->fetchAll();
    }
}
BTW,使用没有聚合函数的GROUP BY time可能会产生不可预测的结果。结果中的每一列都可以来自组中的不同行。

您可以将所有结果连接到一个数组中,而不是二维数组,这相当于在数据库中执行UNION

$all_results = array_merge($all_results, $stmt->fetchAll());

答案 1 :(得分:0)

这是完全错误的:

$stmt=$db2->prepare("SELECT * FROM elfinder_file_".strtolower(:username)." 
                                                  ^^^^^^^^^^^^^^^^^^^^^^^

PHP不知道(或关心)SQL占位符是什么。这是一个彻底的语法错误。

你必须使用

$stmt = blahblah FROM elfinder_file>" . strtolower($var_with_username) . " etc...

就动态表名称而言,数据库不知道您在何处/如何生成查询字符串。它只会在生成后查看查询字符串。 e.g。

$var = 'sometable';
$sql = "SELECT foo FROM bar UNION ALL SELECT baz FROM $var";

将生成完全相同的

SELECT foo FROM bar UNION ALL SELECT baz FROM sometable
数据库收到的

,就像您手动输入该查询一样。

当然,在元级别上,请注意占位符只能代表VALUES。您不能将占位符用于标识符/关键字。