Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/mysql/69.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
MySQL:如何查询复合主键?具体来说,一个不在查询中的?_Mysql_Cakephp_Composite Primary Key_Notin_Phinx - Fatal编程技术网

MySQL:如何查询复合主键?具体来说,一个不在查询中的?

MySQL:如何查询复合主键?具体来说,一个不在查询中的?,mysql,cakephp,composite-primary-key,notin,phinx,Mysql,Cakephp,Composite Primary Key,Notin,Phinx,我有一个comment表和一个comment\u edit表,以及olddb\u edit。简化后,相关表格如下所示: CREATE TABLE `olddb_edit` ( edit_id INT NOT NULL, edit_time INT NOT NULL, edit_text TEXT NOT NULL, PRIMARY KEY (edit_id, edit_time) ) ENGINE=InnoDB; $skippable = array(

我有一个
comment
表和一个
comment\u edit
表,以及
olddb\u edit
。简化后,相关表格如下所示:

CREATE TABLE `olddb_edit` (
    edit_id INT NOT NULL,
    edit_time INT NOT NULL,
    edit_text TEXT NOT NULL,

    PRIMARY KEY (edit_id, edit_time)

) ENGINE=InnoDB;
$skippable = array(
    array('id' => 707969,   'time' => 1434462225),
    array('id' => 707969,   'time' => 1434462463),
    array('id' => 707969,   'time' => 1434462551),
);
现在我想将内容从另一个DB迁移到编辑表中,但跳过一些表行,如测试注释。我使用CakePHP来实现这一点(实际上是Phinx)

通常,这就足够了:

$skippable = array(
    12345, 23456, 34567, 45678,
);
$rows = $this->getQueryBuilder()
    ->select('*')
    ->from('olddb_comment')
    ->where(array(
        'comment_id NOT IN' => $skippable,
    ))
    ->execute()
    ->fetchAll('assoc')
;
但是一个简单的
notin
子句显然不适用于复合主键

我在想,
$skippable
数组应该如下所示:

CREATE TABLE `olddb_edit` (
    edit_id INT NOT NULL,
    edit_time INT NOT NULL,
    edit_text TEXT NOT NULL,

    PRIMARY KEY (edit_id, edit_time)

) ENGINE=InnoDB;
$skippable = array(
    array('id' => 707969,   'time' => 1434462225),
    array('id' => 707969,   'time' => 1434462463),
    array('id' => 707969,   'time' => 1434462551),
);
然后我将通过for循环或其他方式运行where子句。但老实说,我甚至不知道如何在香草MySQL中做到这一点


可能已经发布了一个解决方案,但我找不到任何解决方案(除了特定于其他应用程序的解决方案)。我想这个算法不是我的朋友。

没关系,我在制定问题的时候自己弄明白了。不管怎样,我会把答案贴出来,给其他有类似问题的人


首先,香草MySQL。如果您不在(imo)中分解
,这与您想象的一样直观:


使用CakePHP/Phinx查询生成器,可以使用匿名函数、for循环和not或构造:

$qb = $this->getQueryBuilder()
    ->select('*')
    ->from('olddb_edit')
    ->where(array(
        'edit_some_other_optional_condition = 1',
    ))

    // also skip skippables.
    ->where(function($exp) use ($skippable) {
        $ORed = array();
        foreach ($skippable as $edit) {
            array_push($ORed, array(
                'edit_id'   => $edit['id'],
                'edit_time' => $edit['time'],
            ));
        }
        return $exp->not($exp->or_($ORed));
    })
;

更新:根据@ndm的评论,我使用TupleComparison提供了一个令人满意的解决方案(@ndm,如果您愿意,请随时发布您的答案。我将删除/编辑我的答案,然后选择您的答案。您应该获得此荣誉)


您的查询的计算结果如下:;你确定这就是你想要的吗

select edit_id 
     , edit_time
     , edit_text 
  from olddb_edit 
 where 
     (
       (
         (edit_id <> 707969) 
      or (edit_time <> 1434461454)
       ) 
   and (
         (edit_id <> 707969) 
      or (edit_time <> 1434461503)
       ) 
   and (
         (edit_id <> 707969) 
      or (edit_time <> 1434461925)
        )
      );
选择编辑\u id
,编辑时间
,编辑文本
从olddb_编辑
哪里
(
(
(编辑编号707969)
或(编辑时间1434461454)
) 
及(
(编辑编号707969)
或(编辑时间1434461503)
) 
及(
(编辑编号707969)
或(编辑时间1434461925)
)
);

在SQL中,元组也可以工作,而不是展开不在
中的
。比如:
(edit\u id,edit\u time)notin((707969143441454),(707969143441503),…)
@stickybit我发现
或不
非常混乱,所以我可能弄错了,但我认为你的查询在逻辑上是不同的(很可能是OP想要的)。@草莓:嗯,我不知道。。。首先要注意的是,我在这个答案中引用了SQL,不是问题中的任何东西,也不是任何PHP的东西,如果不清楚的话。然后我的推理是:
NOT
后面括号中的所有内容都可以用元组表示为
in
。使用元组覆盖
s,然后它是一组具有相同左操作数的
s,可以在
中表示为
。所以我们得到了
而不是(…IN…
)。这可以简化为
不在…
中。当然,我可能在某个地方错了。也许你可以构造一个反例?我不知道
不在
支持的元组中,或者这是一件事(在
插入
语句之外)。我在dev.mysql.com上找不到(现在仍然找不到)任何关于这方面的官方文档……我会调查一下,看看这其中是否有CakePHP的东西。有一个用于元组比较的表达式:请问一个特定的问题:你到底在哪里。对于代码问题,给出一个give a--cut&paste&runnable代码,包括作为代码输入的最小代表性示例;期望和实际输出(包括逐字记录错误消息);标签和版本;清晰的说明和解释。对于SQL、DBMS和DDL(包括约束和索引)以及作为表格式的代码输入。查询时不需要PS键。连接基于条件,而不是关键点。在for子查询中,接受的是行,而不是键。是否为多列是DBMS特有的。“典型存在”是一个更好的选择。这是一个奇怪的看待它的方式,但本质上是:是的。这就是我想要的。同时是每个可跳过行的求反的表行。毕竟,这就是不在
中的
是什么。