存储过程

时间:2015-09-16 17:50:42

标签: mysql stored-procedures

我一直在谷歌搜索找到答案但却找不到任何答案。我有一个游标语句,用于提取数据库中存在的表的名称。

目标是: 具有2个参数的存储过程,database1和database2 比较两个数据库并输出差异。 数据库名称是制表符/空格分隔

BEGIN
DECLARE done INT DEFAULT FALSE;
DECLARE db_tables VARCHAR(256);

DECLARE cursor1 CURSOR FOR 
        SELECT TABLE_NAME, TABLE_SCHEMA
        FROM information_schema.tables  
        WHERE TABLE_SCHEMA = db1
        AND TABLE_TYPE = 'BASE TABLE';

DECLARE CONTINUE HANDLER FOR NOT FOUND SET done = TRUE;

OPEN cursor1;
FETCH cursor1 into db_tables;

WHILE done = FALSE DO
SET query1 = SELECT * FROM db1 WHERE table1 IN(table_name);
END WHILE;
CLOSE cursor1;

END

1 个答案:

答案 0 :(得分:0)

这使用INFORMATION_SCHEMA.TABLES信息

架构

create database db1;
create database db2;

create table db1.s1 (id int);
create table db1.s2 (id int);
create table db1.s3 (id int);

create table db2.s2 (id int);
create table db2.s3 (id int);
create table db2.s4 (id int);

查询

select t1.table_name, 2 as 'not in this one'
from INFORMATION_SCHEMA.TABLES t1
where t1.table_schema='db1'
and not exists (select * from INFORMATION_SCHEMA.TABLES t2 where t2.table_schema='db2' and t2.table_name=t1.table_name)
union
select t1.table_name, 1 as 'not in this one'
from INFORMATION_SCHEMA.TABLES t1
where t1.table_schema='db2'
and not exists (select * from INFORMATION_SCHEMA.TABLES t2 where t2.table_schema='db1' and t2.table_name=t1.table_name)

结果

+------------+-----------------+
| table_name | not in this one |
+------------+-----------------+
| s1         |               2 |
| s4         |               1 |
+------------+-----------------+

这意味着表s1位于数据库db1中,但不在db2中,而表s4位于数据库db2中,但不是在db1

存储过程

delimiter $$
create procedure showDBDiffInTableNames
( x1 varchar(40),x2 varchar(40) )
BEGIN
    -- 
    -- passed parameters, x1 is a string containing the name of a database
    -- x2 is a string containing the name of another database
    --
    select t1.table_name, 2 as 'not in this one'
    from INFORMATION_SCHEMA.TABLES t1
    where t1.table_schema=x1
    and not exists (select * from INFORMATION_SCHEMA.TABLES t2 where t2.table_schema=x2 and t2.table_name=t1.table_name)
    union
    select t1.table_name, 1 as 'not in this one'
    from INFORMATION_SCHEMA.TABLES t1
    where t1.table_schema=x2
    and not exists (select * from INFORMATION_SCHEMA.TABLES t2 where t2.table_schema=x1 and t2.table_name=t1.table_name);
END
$$
DELIMITER ;

测试它:

call showDBDiffInTableNames('x1','x2');

结果相同

t1t2只是表别名。请参见手册页here。从手册页:

  

以下列表描述了何时需要考虑的一般因素   写连接。

     

可以使用tbl_name AS alias_name或表别名表参考   tbl_name alias_name:

     

...

如果提前知道,我正在寻找两个或更多表,我几乎从不写没有别名的查询。它减少了打字。它们在自连接中尤为常见(在同一个表中)。您需要一种方法来区分您正在处理的是哪一个,以从查询中删除不明确的错误。这就是为什么别名在那里。另外,你会注意到桌子在两次之后消失了。

有两种方法可以编写它,如上面的粉色/桃色块所示。