找出oracle中两个大表之间的差异

时间:2013-12-23 20:36:19

标签: sql database oracle plsql large-data

我有两个不同的表,比如oracle中的表A和B,每个表中有大约1500万条记录。 Table A(a,b,c,d)和。{ Table B(e,f,g,h)

目标是编写一个存储过程来检查表A中的每个记录是否也存在于表B中,反之亦然。应将这两者之间的差异插入第三个表格中。

我的问题是  如果column a包含某个字符串(0311),则应将Table A中的column e与表E中列e和f的连接进行比较,  如果不是,我必须将其与column f进行比较。

Column b应与column g中的table B进行比较 我还必须将column c中的table Acolumn g中的table B进行比较,如果两者不匹配column d则应与{{1}进行比较}}

最快的方法是什么?

例如这两个匹配:

column g

或:

Table A: 9353456789,03117884657,12082200003035,12082123595535
Table B: 9353456789,0311,7884657,12082200003035

不需要连接且匹配的记录示例:

Table A: 9353456789,03117884657,12082200003035,12082123595535
Table B: 9353456789,0311,7884657,12082123595535

2 个答案:

答案 0 :(得分:1)

我这样做是作为两个陈述,但可以合并

Select a.* 
from tablea a left join tableb b on a.a = 
 case when e = 'string' then b.e || b.f else b.f end 
and ...
where b.e is null

左连接将返回空值,其中在表b中找不到行,因此这将显示表a中不包含表b的行列表。将语句更改为右连接并选择b。*并且您将看到b中的内容但不包含在内。

语句可以变成'create table as',它将使用select语句的结果创建一个新表。

我把...和你的条件有点混淆,你只需要使用case语句来选择你想要比较/加入的列。

答案 1 :(得分:1)

SQL Fiddle

Oracle 11g R2架构设置

CREATE TABLE TableA ( a VARCHAR2(20), b VARCHAR2(20), c VARCHAR2(20), d VARCHAR2(20) );
CREATE TABLE TableB ( e VARCHAR2(20), f VARCHAR2(20), g VARCHAR2(20), h VARCHAR2(20) );
CREATE TABLE TableC ( i VARCHAR2(20), j VARCHAR2(20), k VARCHAR2(20), l VARCHAR2(20) );

INSERT INTO TableA
          SELECT '9353456789','03117884657','12082200003035','12082123595535' FROM DUAL
UNION ALL SELECT '9353456789','03617884657','12082200003035','12082123595535' FROM DUAL
UNION ALL SELECT '9353456789','03617884657','12082200003034','12082123595534' FROM DUAL;

INSERT INTO TableB
          SELECT '9353456789','0311','7884657','12082200003035' FROM DUAL
UNION ALL SELECT '9353456789','0311','7884657','12082123595535' FROM DUAL
UNION ALL SELECT '9353456789','0361','03617884657','12082200003035' FROM DUAL
UNION ALL SELECT '9353456789','0361','03617884657','12082200003036' FROM DUAL;

查询1

要插入行 - 使用您的要求作为连接条件,在两个表之间使用INSERT INTO... SELECT执行FULL OUTER JOIN;然后对于与TableA(a, b, c, d)不匹配的行,NULLTableB(e, f, g, h)都将为NULL,这可以在WHERE条件中使用只获得不匹配的行。最后,为了不返回NULL值,COALESCE()用于返回的值。

INSERT INTO TableC
    SELECT COALESCE( ta.a, tb.e ) AS i,
           COALESCE( ta.b, tb.f ) AS j,
           COALESCE( ta.c, tb.g ) AS k,
           COALESCE( ta.d, tb.h ) AS l
    FROM TableA ta
         FULL OUTER JOIN
         TableB tb
         ON (    ta.a = tb.e
             AND ta.b = CASE tb.f WHEN '0311' THEN tb.f || tb.g ELSE tb.g END
             AND ( ta.c = tb.h OR ta.d = tb.h )
            )
    WHERE ta.a IS NULL
    OR    tb.e IS NULL;

查询2

SELECT * FROM TableC

<强> Results

|          I |           J |              K |              L |
|------------|-------------|----------------|----------------|
| 9353456789 | 03617884657 | 12082200003034 | 12082123595534 |
| 9353456789 |        0361 |    03617884657 | 12082200003036 |