Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/oracle/10.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
ORACLE 12.2.01从名称相似的不同表中选择列-->;使用内部列标识符_Oracle_Select_Identifier - Fatal编程技术网

ORACLE 12.2.01从名称相似的不同表中选择列-->;使用内部列标识符

ORACLE 12.2.01从名称相似的不同表中选择列-->;使用内部列标识符,oracle,select,identifier,Oracle,Select,Identifier,我编写了一个执行并集的SELECT,并在每个并集部分使用一些连接。连接的表具有部分相同的列标识符。 如果执行“选择*”,ORACLE决定显示内部列名,而不是“真实”列名 为了显示效果,我创建了两个表(具有部分相似的列标识符“TID”和“TNAME”),并用一些数据填充它们: create table table_one (tid number(10), tname varchar2(10), t2id number(10)); create table table_two (tid number

我编写了一个执行并集的SELECT,并在每个并集部分使用一些连接。连接的表具有部分相同的列标识符。 如果执行“选择*”,ORACLE决定显示内部列名,而不是“真实”列名

为了显示效果,我创建了两个表(具有部分相似的列标识符“TID”和“TNAME”),并用一些数据填充它们:

create table table_one (tid number(10), tname varchar2(10), t2id number(10));
create table table_two (tid number(10), tname varchar2(10));

insert into table_two values (1,'one');
insert into table_two values (2,'two');
insert into table_two values (3,'three');

insert into table_one values (1,'eins',1);
insert into table_one values (2,'zwei',2);
insert into table_one values (3,'drei',3);
之后,我用以下语句选择了列:

select * 
from table_one 
inner join table_two on table_two.tid = table_one.t2id
where table_one.tid = 1
union
select * 
from table_one 
inner join table_two on table_two.tid = table_one.t2id
where table_one.tid = 2;
create table table_3 (tid number(10), tname varchar2(10), t4id number(10));
create table table_4 (tid number(10), tname varchar2(10));

insert into table_4 values (1,'one');
insert into table_4 values (2,'two');
insert into table_4 values (3,'three');

insert into table_3 values (1,'eins',1);
insert into table_3 values (2,'zwei',2);
insert into table_3 values (3,'drei',3);

select * 
from table_one 
inner join table_two on table_two.tid = table_one.t2id
where table_one.tid = 1
union
select * 
from table_3
inner join table_4 on table_4.tid = table_3.t4id
where table_3.tid = 2;

select * 
from table_one 
inner join table_two on table_two.tid = table_one.t2id
where table_one.tid = 1
union
select * 
from table_3
inner join table_4 on table_4.tid = table_3.t4id
where table_3.tid = 2;
得到了这个令人困惑的结果:

QCSJ_C000000000300000 QCSJ_C000000000300002       T2ID QCSJ_C000000000300001 QCSJ_C000000000300004
                    1 eins                           1                     1 one
                    2 zwei                           2                     2 two
当使用tablename编写语句以指定列时,一切都按照我的预期工作:

select table_one.* , table_two.*
from table_one 
inner join table_two on table_two.tid = table_one.t2id
where table_one.tid = 1
minus
select * 
from table_one 
inner join table_two on table_two.tid = table_one.t2id
where table_one.tid = 2;
有人能解释一下吗

我用另外两个表扩展了我的测试,以防止在语句中重复使用表:

select * 
from table_one 
inner join table_two on table_two.tid = table_one.t2id
where table_one.tid = 1
union
select * 
from table_one 
inner join table_two on table_two.tid = table_one.t2id
where table_one.tid = 2;
create table table_3 (tid number(10), tname varchar2(10), t4id number(10));
create table table_4 (tid number(10), tname varchar2(10));

insert into table_4 values (1,'one');
insert into table_4 values (2,'two');
insert into table_4 values (3,'three');

insert into table_3 values (1,'eins',1);
insert into table_3 values (2,'zwei',2);
insert into table_3 values (3,'drei',3);

select * 
from table_one 
inner join table_two on table_two.tid = table_one.t2id
where table_one.tid = 1
union
select * 
from table_3
inner join table_4 on table_4.tid = table_3.t4id
where table_3.tid = 2;

select * 
from table_one 
inner join table_two on table_two.tid = table_one.t2id
where table_one.tid = 1
union
select * 
from table_3
inner join table_4 on table_4.tid = table_3.t4id
where table_3.tid = 2;
结果是一样的。Oracle使用内部标识符。

根据Oracle(DocId 2658003.1),当满足以下三个条件时,会发生这种情况:

  • ANSI连接
  • 工会/全体工会
  • 同一个表在查询中多次出现
  • 在Oracle转换ANSI样式联接时,内部使用“QCSJ__C”作为一个单独的名称

    编辑:

    找到了一个最小的示例:

    SELECT * FROM dual d1 JOIN dual d2 ON d1.dummy=d2.dummy
    UNION
    SELECT * FROM dual d1 JOIN dual d2 ON d1.dummy=d2.dummy;
    
    QCSJ_C000000000300000 QCSJ_C000000000300001
    X                     X
    
    可以通过使用非ANSI连接语法进行修复:

    SELECT * FROM dual d1, dual d2 WHERE d1.dummy=d2.dummy
    UNION
    SELECT * FROM dual d1, dual d2 WHERE d1.dummy=d2.dummy;
    
    DUMMY DUMMY_1
    X     X
    
    或者,最好使用列名而不是
    *

    SELECT d1.dummy, d2.dummy FROM dual d1 JOIN dual d2 ON d1.dummy=d2.dummy
    UNION
    SELECT d1.dummy, d2.dummy FROM dual d1 JOIN dual d2 ON d1.dummy=d2.dummy;
    
    DUMMY DUMMY_1
    X     X
    
    有趣

    但是,我决不会将set运算符(
    UNION
    UNION ALL
    INTERSECT
    减号
    )与星号(
    *
    )一起使用

    列的顺序可能会改变,可能不是由您更改,而是由对数据库进行维护的人员更改,或者通过使用导出/导入等方式将数据库迁移到新系统。简单示例:

    CREATE TABLE t (a INT, b INT, c INT);
    SELECT * FROM t;
    A B C
    
    ALTER TABLE t MODIFY b INVISIBLE;
    ALTER TABLE t MODIFY b VISIBLE;
    SELECT * FROM t;
    A C B
    

    顺便说一句,在现实生活中,我决不会在工会中使用
    SELECT*
    。太危险了,如果在其中一个表中添加或删除新列,查询将更改或中断。Oracle内部使用
    QCSJ_C000
    作为列别名,以避免重复名称,并使其唯一,因为您使用
    *
    而不是显式列名。@LalitKumarB是的,我知道。但在第二条语句中,也有不准确的列名。ORACLE提供了具有类似名称的列(或在某些应用程序中为Quest TOAD,其中_1为TID_1和TNAME_1)。在我看来,内部名称为QCSJ_C000的行为是新的……不,它不是新的。DocId 2658003.1引用了Oracle版本11.2.0.4。@virtualbee不,这不是新行为。参见“wolφi”给出的文档。这是一种非常古老且众所周知的行为。我扩展了测试以防止表名的双重使用(见上文)。结果是一样的,ORACLE使用内部列名。能否提供到DocId 2658003.1的链接?该文档来自support.ORACLE.com。很遗憾,您需要一份有效的支持合同才能阅读支持文档。是的,我知道。但我是唯一一个改变数据库的人;)并且该语句仅在测试用例中使用,而不是在应用程序中使用。