精华内容
下载资源
问答
  • 今天做Schema评审的时候发现一个很奇怪的现象,也许是用工具生成的SQL语句,清一色的如下: CREATE TABLE table_name ( id NUMBER NOT NULL, ...CREATE INDEX table_name_PK ON table_name(ID) ; ALTER T...

    今天做Schema评审的时候发现一个很奇怪的现象,也许是用工具生成的SQL语句,清一色的如下:

    CREATE TABLE table_name (
        id          NUMBER          NOT NULL,
        ......
        ......
    ) ;
     
    CREATE INDEX table_name_PK ON table_name(ID) ;
    ALTER TABLE table_name 
      ADD CONSTRAINT table_name_PK PRIMARY KEY (ID) 
      USING INDEX table_name_PK ;

    通常来说主键(Primary Key,PK)的index是unique index,而现在变成了non-unique index,这有什么不同呢?

    于是我建了两张1000万数据的表,并用两种不同的index设定为PK的index,语句如下:

    create table tab1000w01 
    as
    select level id,'killkill Hello world' data
    from dual connect by level<=1000*10000;
     
    create table tab1000w02 
    as
    select level id,'killkill Hello world' data
    from dual connect by level<=1000*10000;
     
    CREATE UNIQUE INDEX tab1000w01_pk ON tab1000w01 (PK_ID)  ;
    ALTER TABLE  tab1000w01 ADD CONSTRAINT tab1000w01_PK PRIMARY KEY (PK_ID) USING INDEX tab1000w01_pk ;
     
    CREATE INDEX tab1000w02_pk ON tab500w02 (PK_ID)  ;
    ALTER TABLE  tab1000w02 ADD CONSTRAINT tab1000w02_PK PRIMARY KEY (PK_ID) USING INDEX tab1000w02_pk ;

    以下是按照PK查找数据的语句:

    select * from tab1000w01 where id=34567;
     
    -------------------------------------------------------------------------------------------------
    | Id  | Operation                   | Name              | Rows  | Bytes | Cost (%CPU)| Time     |
    -------------------------------------------------------------------------------------------------
    |   0 | SELECT STATEMENT            |                   |     1 |    35 |     3   (0)| 00:00:01 |
    |   1 |  TABLE ACCESS BY INDEX ROWID| TAB1000W01        |     1 |    35 |     3   (0)| 00:00:01 |
    |*  2 |   INDEX UNIQUE SCAN         | IDX_TAB1000W01_PK |     1 |       |     2   (0)| 00:00:01 |
    -------------------------------------------------------------------------------------------------
     
    Predicate Information (identified by operation id):
    ---------------------------------------------------
     
       2 - access("ID"=34567)
     
    Statistics
    ----------------------------------------------------------
              0  recursive calls
              0  db block gets
              4  consistent gets
     
     
    select * from tab1000w02 where id=34567;
     
    -------------------------------------------------------------------------------------------------
    | Id  | Operation                   | Name              | Rows  | Bytes | Cost (%CPU)| Time     |
    -------------------------------------------------------------------------------------------------
    |   0 | SELECT STATEMENT            |                   |     1 |    35 |     3   (0)| 00:00:01 |
    |   1 |  TABLE ACCESS BY INDEX ROWID| TAB1000W02        |     1 |    35 |     3   (0)| 00:00:01 |
    |*  2 |   INDEX RANGE SCAN          | IDX_TAB1000W02_PK |     1 |       |     2   (0)| 00:00:01 |
    -------------------------------------------------------------------------------------------------
     
    Predicate Information (identified by operation id):
    ---------------------------------------------------
     
       2 - access("ID"=34567)
     
    Statistics
    ----------------------------------------------------------
              0  recursive calls
              0  db block gets
              5  consistent gets

    从执行计划来看,一个是index unique scan,一个是index range scan,从consistent gets来看,一个是4,一个是5,使用unique index节省了1个,不要少看这1个consistent gets,它可是占了总体的20%啊。

    不过这是为什么呢?这篇文章很好地介绍这两种索引的异同:Differences Between Unique and Non-Unique Indexes,说到底是这两种索引的结构不同。引用一下这篇文章的分析:

    Leaf block dump
    ===============
    header address 143336028=0x88b225c
    kdxcolev 0
    KDXCOLEV Flags = - - -
    kdxcolok 0
    kdxcoopc 0x80: opcode=0: iot flags=--- is converted=Y
    kdxconco 2
    kdxcosdc 0
    kdxconro 500
    kdxcofbo 1036=0x40c
    kdxcofeo 1042=0x412
    kdxcoavs 6
    kdxlespl 0
    kdxlende 0
    kdxlenxt 75520140=0x480588c
    kdxleprv 75520138=0x480588a
    kdxledsz 0
    kdxlebksz 8036
    row#0[8022] flag: ------, lock: 0, len=14     <=== length is 14 bytes for the index row entry
    col 0; len 4; (4):  c3 60 61 1c
    col 1; len 6; (6):  04 80 50 3c 01 06         <=== rowid is stored as a second column for the index row entry
    row#1[8008] flag: ------, lock: 0, len=14
    col 0; len 4; (4):  c3 60 61 1d
    col 1; len 6; (6):  04 80 50 3c 01 07

    non-unique index将 rowid 作为一个字段和数据字段组合成一个“唯一、复合”索引

     

    而unique index的结构如下:

    Leaf block dump
    ===============
    header address 143336028=0x88b225c
    kdxcolev 0
    KDXCOLEV Flags = - - -
    kdxcolok 0
    kdxcoopc 0x80: opcode=0: iot flags=--- is converted=Y
    kdxconco 1
    kdxcosdc 0
    kdxconro 533
    kdxcofbo 1102=0x44e
    kdxcofeo 1112=0x458
    kdxcoavs 10
    kdxlespl 0
    kdxlende 0
    kdxlenxt 75527436=0x480750c
    kdxleprv 75527434=0x480750a
    kdxledsz 6
    kdxlebksz 8036
    row#0[8023] flag: ------, lock: 0, len=13, data:(6):  04 80 5e 34 02 82    <=== length is 13 byes and rowid not stored as a second column entry
    col 0; len 4; (4):  c3 60 30 2c
    row#1[8010] flag: ------, lock: 0, len=13, data:(6):  04 80 5e 34 02 83
    col 0; len 4; (4):  c3 60 30 2d

    从dump文件中可以看到结构不同导致index中的entry的长度是不一样的,unique index稍稍短一点,所以每个block可以容纳更多的index entry,从宏观来看unique index更小一点。

     

    不像 MySQL 唯一性约束是由唯一性索引实现,Oracle 的索引和约束是分开对待的。

    如果某一天,需要将某个唯一性约束(Unique Key)变为不约束,unique index 只能删除重建了,一般变更的语句会变成这样:

    create table table_xxx .......;
    
    create index uk_xx on table_xx ( col ) online ;
    
    # 以上实现了一个唯一性约束
    
    # 突然来了一个需求,要将这个唯一性约束去掉,但是按 col 列查的语句海得跑 -_-
    
    create index idx_xx on table_xx ( col , 'c' ) online ;
    
    drop index uk_xx ;
    
    create index idx_col on table_xx ( col ) online ; 
    
    drop index idx_xx ;

    没有看错,索引建两次和删索引两次,第一次建复合索引是因为 Oracle 不允许两个索引的索引列信息一致,只能加一个无关重要的东西卡位。

    针对这种奇葩需求,使用 non unique index + unique constraint 更灵活:

    create table table_xxx .......;
    
    create index uk_xx on table_xx ( col ) online ;
    
    alter table table_xx add constraint uk_xx unique( col ) using uk_xx ;
    
    # 以上实现了一个唯一性约束
    
    
    # 突然来了一个需求,要将这个唯一性约束去掉,但是按 col 列查的语句海得跑 -_-
    
    alter table table_xx drop constraint uk_xx ;
    
    

    从维护的角度来说,特别是大表的情况下,推荐第二种方式。

     

    转载请注明出处: https://blog.csdn.net/killlkilll/article/details/97966651

     

    展开全文
  • INDEX UNIQUE SCAN 如果表上有唯一索引, 搜索索引列时会用上INDEX UNIQUE SCAN 原来Index Unique Scan和Index Range Scan在B Tree上的搜索路径是一样的 只是Index Unique Scan在找到应该含有要找的Index Key的...
           ㈠ INDEX UNIQUE SCAN
           
           
    果表上有唯一索引, 搜索索引列时会用上INDEX UNIQUE SCAN
           
           原来Index Unique Scan和Index Range Scan在B Tree上的搜索路径是一样的
           只是Index Unique Scan在找到应该含有要找的Index Key的block后便停止了搜索,因为该键是唯一的
           而Index Range Scan还要循着指针继续找下去直到条件不满足时
           
           Oracle9i Database Performance Tuning Guide and Reference提到:
           This access path is used when all columns of a unique (B-tree) index are specified with equality conditions

           下面测试一下这句话的真实性:  

    hr@ORCL> create table t (id number,name varchar2(10));
    hr@ORCL> create unique index ind_t on t (id);
    hr@ORCL> insert into t values(1,'a');
    hr@ORCL> insert into t values(2,'b');
    hr@ORCL> commit;
    hr@ORCL> set autot trace exp
    hr@ORCL> select * from t where id=1;
    
    Execution Plan
    ----------------------------------------------------------
    Plan hash value: 1366100657
    
    -------------------------------------------------------------------------------------
    | Id  | Operation                   | Name  | Rows  | Bytes | Cost (%CPU)| Time     |
    -------------------------------------------------------------------------------------
    |   0 | SELECT STATEMENT            |       |     1 |    20 |     1   (0)| 00:00:01 |
    |   1 |  TABLE ACCESS BY INDEX ROWID| T     |     1 |    20 |     1   (0)| 00:00:01 |
    |*  2 |   INDEX UNIQUE SCAN         | IND_T |     1 |       |     1   (0)| 00:00:01 |
    -------------------------------------------------------------------------------------
    hr@ORCL> drop index ind_t;
    hr@ORCL> create index ind_t on t (id,name);
    hr@ORCL> analyze index ind_t compute statistics;
    hr@ORCL> select * from t where id=1;
    
    Execution Plan
    ----------------------------------------------------------
    Plan hash value: 3131770069
    
    --------------------------------------------------------------------------
    | Id  | Operation        | Name  | Rows  | Bytes | Cost (%CPU)| Time     |
    --------------------------------------------------------------------------
    |   0 | SELECT STATEMENT |       |     1 |    20 |     1   (0)| 00:00:01 |
    |*  1 |  INDEX RANGE SCAN| IND_T |     1 |    20 |     1   (0)| 00:00:01 |
    --------------------------------------------------------------------------

           由此,B-Tree结构的unique index上的所有索引列都要被指定时,才会使用index unique scan来访问


           ㈡ INDEX FULL SCAN和 INDEX FAST  FULL SCAN
              
              一句SQL中,如果我们想搜索的列都包含在索引里面的话
              那么Index Full Scan 和 Index Fast Full Scan 都可以被采用代替Full Table Scan
              有索引排序的时候,优化器可能会偏向于Index Full Scan
              
              如果Select 列表中数据都可来自于索引中包含的字段,则通常容易选择Index Fast Full Scan
              这样出来的数据是根据索引 的 extent 为单元,无顺序的
              扫描block包含了所有枝节点,不区分是否叶子节点。可以做多块顺序扫描,一个io 包含多个block
              
              Index Full Scan 是根据索引的叶子节点顺序获取叶子节点信息然后获得数据(通常还去表中获取数据)
              这样出来的数据是有序的,并且除了定位第一个叶子节点走了根和枝节点block外
              其他叶子节点只由上一个叶子节点的next 指针获得,这样一个索引叶子block就可产生一个io,是离散读
              
              10g在Index Full Scan阶段就把不符合记录的数据先给过滤掉了,最后只有符合条件的rowid做回表
              而9i下,Oracle就比较傻了,Index Full Scan的阶段实际上什么也没做
              只是把所有的rowid都给得到,然后根据得到的rowid从表中取出数据,再过滤掉不符合条件的记录
              
              INDEX_FFS使用多块读,所以在大部分时候,INDEX_FFS速度应该会比单块读的INDEX_FS要快
              
              Index Full Scan将会按逻辑的顺序访问各个索引节点,结果集已经按照索引键值顺序排序,不需要单独排序
              Index Fast Full Scan时索引块通过多块进行读取,结果集是无序的
              所以,如果结果集需要排序那会使用INDEX_FS,如果结果集不需要排序则会使用INDEX_FFS
             
              
              INDEX FULL SCAN  
              HINT写法:INDEX(表名 索引名)或者 INDEX_FS(表名 索引名)
              原理:Oracle定位到索引的ROOT BLOCK,然后到BRANCH BLOCK(如果有的话),再定位到第一个LEAF BLOCK
                        然后根据LEAF BLOCK的双向链表顺序读取。它所读取的块都是有顺序的,也是经过排序的
              
              
              INDEX FAST FULL SCAN    
              HINT写法:INDEX_FFS(表名 索引名)
              原理:从段头开始,读取包含位图块,ROOT BLOCK,所有的BRANCH BLOCK,LEAF BLOCK
                         读取的顺序完全有物理存储位置决定,并采取多块读,每次读取DB_FILE_MULTIBLOCK_READ_COUNT个块
                         IFFS的成本计算公式是:
                         leaf_blocks/k (k依赖于db_file_multiblock_read_count,leaf_blocks依赖于索引统计信息)
                        查询某个表记录总数的时候,往往基于PRIMARY KEY的INDEX FAST FULL SCAN是最有效的

    sys@ORCL> select index_name,blevel,leaf_blocks from user_indexes where table_name=upper('T');
    
    INDEX_NAME                         BLEVEL LEAF_BLOCKS
    ------------------------------ ---------- -----------
    IDX_T                                   1         282

              FAST是多块读,结果集无顺序,如果需要排序则会多一步sort order by;FULL SCAN是单块读,有顺序,可避免ORDER BY成本    
              Performance Tuning Guide中描述如下:
              Index Full Scan可以避免排序操作,在如下情况下,优化器将使用IFS
                1.若谓词引用了索引中的字段
                2.若查询中的所有字段都包含在索引中,并且索引字段中至少有一个字段非空
         
              Index Fast Full Scan
              查询中的所有字段都包含在索引中且至少一个索引列有非空约束的情况下,才会进行IFFS
              IFFS只访问索引,不需要访问数据表,通过读取多个数据块的方式读取整个索引,并不是根据索引的键值进行排序
              如果加个ORDER BY,则FAST会变成IFS,如果索引中没有完全包含要查询的列,或可能INDEX FULL SCAN,或可能直接访问表
              IFFS通过读取多个数据块的方式读取整个索引,且可进行并行处理,相关数据并不是根据索引的键值进行排序
              因此,速度比IFS快,但它不能用于避免排序操作

    展开全文
  • index unique scan 与index range scan等的区别  存取Oracle当中扫描数据的方法(一) Oracle 是一个面向Internet计算环境的数据库。它是在数据库领域一直处于领先地位的甲骨文公司的产品。可以说Oracle关系...

    index unique scan 与index range scan等的区别

     存取Oracle当中扫描数据的方法(一)

    Oracle 是一个面向Internet计算环境的数据库。它是在数据库领域一直处于领先地位的甲骨文公司的产品。可以说Oracle关系数据库系统是目前世界上流行的关系数据库管理系统,本文将对oracle当中扫描数据的存取方法进行介绍。

    1) 全表扫描(Full Table Scans, FTS)

    为实现全表扫描,Oracle读取表中所有的行,并检查每一行是否满足语句的WHERE限制条件一个多块读操作可以使一次I/O能读取多块数据块(db_block_multiblock_read_count参数设定),而不是只读取一个数据块,这极大的减少了I/O总次数,提高了系统的吞吐量,所以利用多块读的方法可以十分高效地实现全表扫描,而且只有在全表扫描的情况下才能使用多块读操作。在这种访问模式下,每个数据块只被读一次。

    使用FTS的前提条件:在较大的表上不建议使用全表扫描,除非取出数据的比较多,超过总量的5% -- 10%,或你想使用并行查询功能时。

    使用全表扫描的例子: 

     SQL> explain plan for select * from dual;

    Query Plan

    SELECT STATEMENT[CHOOSE] Cost=

    TABLE ACCESS FULL DUAL

    2) 通过ROWID的表存取(Table Access by ROWID或rowid lookup)

    行的ROWID指出了该行所在的数据文件、数据块以及行在该块中的位置,所以通过ROWID来存取数据可以快速定位到目标数据上,是Oracle存取单行数据的最快方法。

    这种存取方法不会用到多块读操作,一次I/O只能读取一个数据块。我们会经常在执行计划中看到该存取方法,如通过索引查询数据。

    使用ROWID存取的方法: 

         SQL> explain plan for select * from dept where rowid = 'AAAAyGAADAAAAATAAF';

    Query Plan

    SELECT STATEMENT [CHOOSE] Cost=1

    TABLE ACCESS BY ROWID DEPT [ANALYZED]

    3)索引扫描(Index Scan或index lookup)

    我们先通过index查找到数据对应的rowid值(对于非唯一索引可能返回多个rowid值),然后根据rowid直接从表中得到具体的数据,这种查找方式称为索引扫描或索引查找(index lookup)。一个rowid唯一的表示一行数据,该行对应的数据块是通过一次i/o得到的,在此情况下该次i/o只会读取一个数据库块。

    在索引中,除了存储每个索引的值外,索引还存储具有此值的行对应的ROWID值。索引扫描可以由2步组成:(1) 扫描索引得到对应的rowid值。 (2) 通过找到的rowid从表中读出具体的数据。每步都是单独的一次I/O,但是对于索引,由于经常使用,绝大多数都已经CACHE到内存中,所以第1步的I/O经常是逻辑I/O,即数据可以从内存中得到。但是对于第2步来说,如果表比较大,则其数据不可能全在内存中,所以其I/O很有可能是物理I/O,这是一个机械操作,相对逻辑I/O来说,是极其费时间的。所以如果多大表进行索引扫描,取出的数据如果大于总量的5% -- 10%,使用索引扫描会效率下降很多。如下列所示: 

         SQL> explain plan for select empno, ename from emp where empno=10;

    Query Plan

    SELECT STATEMENT [CHOOSE] Cost=1

    TABLE ACCESS BY ROWID EMP [ANALYZED]

    INDEX UNIQUE SCAN EMP_I1

    但是如果查询的数据能全在索引中找到,就可以避免进行第2步操作,避免了不必要的I/O,此时即使通过索引扫描取出的数据比较多,效率还是很高的

         SQL> explain plan for select empno from emp where empno=10;-- 只查询empno列值

    Query Plan

    SELECT STATEMENT [CHOOSE] Cost=1

    INDEX UNIQUE SCAN EMP_I1

    存取Oracle当中扫描数据的方法(二)

     

    进一步讲,如果sql语句中对索引列进行排序,因为索引已经预先排序好了,所以在执行计划中不需要再对索引列进行排序

          SQL> explain plan for select empno, ename from emp

    where empno > 7876 order by empno;

    Query Plan

    SELECT STATEMENT[CHOOSE] Cost=1

    TABLE ACCESS BY ROWID EMP [ANALYZED]

    INDEX RANGE SCAN EMP_I1 [ANALYZED]

    从这个例子中可以看到:因为索引是已经排序了的,所以将按照索引的顺序查询出符合条件的行,因此避免了进一步排序操作。

    根据索引的类型与where限制条件的不同,有4种类型的索引扫描:

    索引唯一扫描(index unique scan)

    索引范围扫描(index range scan)

    索引全扫描(index full scan)

    索引快速扫描(index fast full scan)

    (1) 索引唯一扫描(index unique scan)

    通过唯一索引查找一个数值经常返回单个ROWID。如果存在UNIQUE 或PRIMARY KEY 约束(它保证了语句只存取单行)的话,Oracle经常实现唯一性扫描。

    使用唯一性约束的例子:

         SQL> explain plan for

    select empno,ename from emp where empno=10;

    Query Plan

    SELECT STATEMENT [CHOOSE] Cost=1

    TABLE ACCESS BY ROWID EMP [ANALYZED]

    INDEX UNIQUE SCAN EMP_I1

    (2) 索引范围扫描(index range scan)

    使用一个索引存取多行数据,在唯一索引上使用索引范围扫描的典型情况下是在谓词(where限制条件)中使用了范围操作符(如>、<、<>、>=、<=、between)

    使用索引范围扫描的例子:

          SQL> explain plan for select empno,ename from emp

    where empno > 7876 order by empno;

    Query Plan

    SELECT STATEMENT[CHOOSE] Cost=1

    TABLE ACCESS BY ROWID EMP [ANALYZED]

    INDEX RANGE SCAN EMP_I1 [ANALYZED]

    在非唯一索引上,谓词col = 5可能返回多行数据,所以在非唯一索引上都使用索引范围扫描。

    使用index rang scan的3种情况:

    (a) 在唯一索引列上使用了range操作符(> < <> >= <= between)

    (b) 在组合索引上,只使用部分列进行查询,导致查询出多行

    (c) 对非唯一索引列上进行的任何查询。

    (3) 索引全扫描(index full scan)

    与全表扫描对应,也有相应的全索引扫描。而且此时查询出的数据都必须从索引中可以直接得到。

    全索引扫描的例子:

    An Index full scan will not perform single block i/o's and so it may prove to be inefficient.

    e.g.

    Index BE_IX is a concatenated index on big_emp (empno, ename)

    SQL> explain plan for select empno, ename from big_emp order by empno,ename;

    Query Plan

    SELECT STATEMENT[CHOOSE] Cost=26

    INDEX FULL SCAN BE_IX [ANALYZED]

    (4) 索引快速扫描(index fast full scan)

    扫描索引中的所有的数据块,与 index full scan很类似,但是一个显著的区别就是它不对查询出的数据进行排序,即数据不是以排序顺序被返回。在这种存取方法中,可以使用多块读功能,也可以使用并行读入,以便获得最大吞吐量与缩短执行时间。

    索引快速扫描的例子:

    BE_IX索引是一个多列索引: 

         big_emp (empno,ename)

    SQL> explain plan for select empno,ename from big_emp;

    Query Plan

    SELECT STATEMENT[CHOOSE] Cost=1

    INDEX FAST FULL SCAN BE_IX [ANALYZED]

    只选择多列索引的第2列:

         SQL> explain plan for select ename from big_emp;

    Query Plan

    SELECT STATEMENT[CHOOSE] Cost=1

    INDEX FAST FULL SCAN BE_IX [ANALYZED]

    展开全文
  • 【mysql】unique key index区别

    千次阅读 2019-06-30 13:47:31
    关系大致是这样: mysql中的unique约束是通过索引实现的;...在mysql中,使用index或者unique(以及key)都会简历索引,区别在于是否允许重复,这个可以在show index命令中看到。 CREATE TABLE user1(...

    关系大致是这样:

    mysql中的unique约束是通过索引实现的;

    key的含义是概念级别的,意味着唯一性,key的概念等价于unique;

    所以说只要加了unique约束或者key,就会建立一个索引。

    在mysql中,使用index或者unique(以及key)都会简历索引,区别在于是否允许重复,这个可以在show index命令中看到。

     

    CREATE TABLE user1(
      id INT PRIMARY KEY AUTO_INCREMENT COMMENT '主键',
      name VARCHAR(200) COMMENT '姓名',
      age    int COMMENT '年龄',
      unique aaa (`name`, `age`)
    )
    
    CREATE TABLE user1(
      id INT PRIMARY KEY AUTO_INCREMENT COMMENT '主键',
      name VARCHAR(200) COMMENT '姓名',
      age    int COMMENT '年龄',
      constraint aaa unique(`name`, `age`)
    )

    这两种建表语句都会建立一个联合索引:

    mysql> show index from user1;
    +-------+------------+----------+--------------+-------------+-----------+-------------+----------+--------+------+------------+---------+---------------+
    | Table | Non_unique | Key_name | Seq_in_index | Column_name | Collation | Cardinality | Sub_part | Packed | Null | Index_type | Comment | Index_comment |
    +-------+------------+----------+--------------+-------------+-----------+-------------+----------+--------+------+------------+---------+---------------+
    | user1 |          0 | PRIMARY  |            1 | id          | A         |           0 |     NULL | NULL   |      | BTREE      |         |               |
    | user1 |          0 | aaa      |            1 | name        | A         |           0 |     NULL | NULL   | YES  | BTREE      |         |               |
    | user1 |          0 | aaa      |            2 | age         | A         |           0 |     NULL | NULL   | YES  | BTREE      |         |               |
    +-------+------------+----------+--------------+-------------+-----------+-------------+----------+--------+------+------------+---------+---------------+
    3 rows in set (0.00 sec)

    都有一个index,第二列表明这个index是否允许重复。0代表不允许重复。

    那么把这个aaa的unique删掉,建立一个普通的index:

    mysql> drop index aaa on user1;
    Query OK, 0 rows affected (0.02 sec)
    Records: 0  Duplicates: 0  Warnings: 0

    mysql> create index aaa on user1(`name`, `age`);
    Query OK, 0 rows affected (0.02 sec)
    Records: 0  Duplicates: 0  Warnings: 0

    mysql> show index from user1;
    +-------+------------+----------+--------------+-------------+-----------+-------------+----------+--------+------+------------+---------+---------------+
    | Table | Non_unique | Key_name | Seq_in_index | Column_name | Collation | Cardinality | Sub_part | Packed | Null | Index_type | Comment | Index_comment |
    +-------+------------+----------+--------------+-------------+-----------+-------------+----------+--------+------+------------+---------+---------------+
    | user1 |          0 | PRIMARY  |            1 | id          | A         |           0 |     NULL | NULL   |      | BTREE      |         |               |
    | user1 |          1 | aaa      |            1 | name        | A         |           0 |     NULL | NULL   | YES  | BTREE      |         |               |
    | user1 |          1 | aaa      |            2 | age         | A         |           0 |     NULL | NULL   | YES  | BTREE      |         |               |
    +-------+------------+----------+--------------+-------------+-----------+-------------+----------+--------+------+------------+---------+---------------+
    3 rows in set (0.00 sec)

    可以看到仍然有索引,但是第二列为1,表示该index可以允许重复。

     

     

     

    展开全文
  • oracle的indexunique约束

    千次阅读 2019-01-28 10:04:44
    官网对Unique Constraints说明 http://download.oracle.com/docs/cd/E11882_01/server.112/e16508/datainte.htm#CNCPT1642    uniquekey constraint requires that every value in a column or set of column....
  • index unique scan ,是因为建了唯一索引, unique如 :create unique index AA_INDEX on AA_TEST (SID, ITEMVALUE)在执行语句中 where子句必须包括 唯一索引中的所有字段,而不用管select是否是索引中的字段.analyze ...
  • 主要介绍了mysql中key 、primary key 、unique key 与index区别的相关资料,需要的朋友可以参考下
  • oracle Index Unique Range Bitmap

    千次阅读 2015-04-24 10:24:43
    Index Unique Scan唯一索引(B-tree) Index unique scan is one of the most efficient ways of accessing data. This access method is used for returning the data from B-tree indexes. The optimizer c
  • Mysql唯一性索引(Unique Index

    千次阅读 2019-06-19 20:07:11
    ALTER TABLE `table_name` ADD INDEX index_name ( `column` )  普通索引(由关键字KEY或INDEX定义的索引)的唯一任务是加快对数据的访问速度。因此,应该只为那些最经常出现在查询条件(WHEREcolumn=)或排序条件...
  • 如果在一个列上同时建唯一索引和普通索引的话,mysql会自动选择... 普通索引(由关键字KEY或INDEX定义的索引)的唯一任务是加快对数据的访问速度。因此,应该只为那些最经常出现在查询条件(WHEREcolumn=)或排序条
  • oracle创建unique和删除unique

    千次阅读 2019-07-31 15:33:18
    创建unique和删除unique alter table ONEENTERPRISEONEFILE drop unique(name);--删除原来name列的索引 alter table ONEENTERPRISEONEFILE add constraint ENTERPRISESID_UNIQUE unique (name,address);--创建name...
  • index unique scan

    千次阅读 2014-01-26 20:29:17
    INDEX UNIQUE SCAN 索引唯一扫描。单块读 只可能发生在unique index/primary key 等值查找  等待事件:db file sequential read 但是你几乎看不到,因为只读一条数据  HINT 无需指定,有索引会自动走INDEX ...
  • 索引是我们经常使用的一种数据库搜索优化手段。适当的业务操作场景使用适当的索引方案可以...唯一性索引unique index和一般索引normal index最大的差异就是在索引列上增加了一层唯一约束。添加唯一性索引的数据列...
  • 一、MySQL索引类型 MySql常见索引类型有:主键索引、唯一索引、普通索引、全文索引、组合索引 PRIMARY KEY(主键索引) ALTER TABLE `table_name` ADD PRIMARY KEY ( `column` ) ...INDEX(普...
  • primary 是主键 这个就是表的主键了,唯一的不能重复出现 index 是索引 索引就如同书的目录 unique 是唯一约束 标识数据库表中的每条记录 fulltext 全文索引 一个 FULLTEXT 类型索引 spatial 空间索引 这个跟GIS有关
  • Maps uniqueIndex

    千次阅读 2018-09-02 10:16:33
    Maps.uniqueIndex(Iterable,Function)通常针对的场景是:有一组对象,它们在某个属性上分别有独一无二的值,而我们希望能够按照这个属性值查找对象——译者注:这个方法返回一个Map,键为Function返回的属性值,值为...
  • 那这个问题就可以简化为 PRIMARY KEY,UNIQUE KEY 和 INDEX 的区别。而这三者也正好是索引的划分,主键索引,唯一索引和普通索引(INDEX)。 使用 INDEX 来加速从数据库中读取数据。INDEX 通常加在那些 JOIN, WHERE...
  • mysql建立索引UNIQUE_INDEX_FULLTEXT区别 来源:http://www.greensoftcode.net/   PRIMARY 主键,一个表中只能有一个主键,  该键值不能为 NULL ,不能重复 UNIQUE 唯一键(或称 第二辅助键),...
  • pk:主键是约束,满足条件是非空(not null)而且是唯一(unique)的 。 unique index:索引 主要是可以允许有null,不能有重复。 index :索引 可以为null,可以有重复。 ...
  • 主键与唯一索引(unique index)

    万次阅读 2012-06-19 10:02:55
    (1)创建表时,不能在同一个字段上建立两个索引(主键默认建立唯一索引),在需要经常... index tmp_table_index on tmp_table(deal_id),会报错);  a) 主键:该字段没有重复值,且不允许为空  惟一索引:该字段没有
  • 索引是我们经常使用的一种数据库搜索优化手段。适当的业务操作场景使用适当的索引方案可以... 唯一性索引unique index和一般索引normal index最大的差异就是在索引列上增加了一层唯一约束。添加唯一性索引的数据列...
  • school表名要使用tab上面按键的符号 code:为加入索引的字段 alter table `school` add unique (`code`);
  • 根据业务需要给数据库表添加一个多字段联合唯一索引 unique index。使用表的phone, shop_code 字段关联创建。 其中表phone字段允许null,默认为null。 操作: 使用sql执行脚本执行添加索引sql。执行时报错。提示有...
  • create UNIQUE INDEX uniq_index_piwik_log_action_idaction on piwik_log_action(idaction);这样做的好处:1. primary的index不能方便的reindex2. postgres里面的index容易膨胀 转载于:...
  • 原由: 今天在rename表时,特别是表中包含主键索引和唯一索引时也需要将constraint进行rename; 否则在重建回原始表的主键名称时将报错;...|* 2 | INDEX UNIQUE SCAN | UNI_TEST6U | 1 | ...
  • 消息 1505,级别 16,状态 1,第 1 行因为发现对象名称 'dbo.tbCICostDetail' 和索引名称 'PK_tbCICostDetail_1' 有重复的键,所以 CREATE UNIQUE INDEX 语句终止。重复的键值为 (18305247)。消息 1...
  • create index cluster on student(sno) go drop index student.cluster go alter table score drop constraint FK_score1 go alter table score drop constraint FK_score2 go alter table student drop const

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 213,397
精华内容 85,358
关键字:

indexunique