zoukankan      html  css  js  c++  java
  • 数据库查询优化的一些总结

    查询优化经验总结

    对于大表,数据先过滤 再关联 性能最好

    尽量避免全表扫描

    如果根据大表的某个计算结果比较频繁,应该将其作为临时表,缓存结果,比如投资者持仓数据

     

    索引

    索引的基础概念

    在关系数据库中,索引是一种与表有关的数据库结构,它可以使对应于表的SQL语句执行得更快。索引的作用相当于图书的目录,可以根据目录中的页码快速找到所需的内容。

    当表中有大量记录时,若要对表进行查询:

    第一种搜索信息方式是全表搜索,是将所有记录一一取出,和查询条件进行一一对比,然后返回满足条件的记录,这样做会消耗大量数据库系统时间,并造成大量磁盘I/O操作;

    第二种就是在表中建立索引,然后在索引中找到符合查询条件的索引值,最后通过保存在索引中的ROWID(相当于页码)快速找到表中对应的记录。

     

    索引的优点

    1.大大加快数据的检索速度;

    2.创建唯一性索引,保证数据库表中每一行数据的唯一性;

    3.加速表和表之间的连接;

    4.在使用分组和排序子句进行数据检索时,可以显著减少查询中分组和排序的时间。

     

    索引的缺点

    1.索引需要占物理空间。

    2.当对表中的数据进行增加、删除和修改的时候,索引也要动态的维护,降低了数据的维护速度。

     

    Teradata中PI使用的一个例子

    PI索引不仅对查询有影响,对数据迁移也会造成很大的影响

     

    一个千万级数据量的表,本想通过如下语句将数据汇总并导入一个新表中:
    CREATE SET TABLE DSS_TTemp.STKT_AL_SELL_DAILY_AGG_MONTH
    AS
    (
    SELECT cast((cast(Day_Id as format 'YYYYMM')) as char(6)) as Day_Id,
        cast((cast(Tkg_Dt as format 'YYYYMM')) as char(6) ) as Tkg_Dt,
        Agc_IATA_Cd,Agc_Cty_Cd,Carr_Cd,Arrv_Airpt_Cd,Arrv_Cty_Cd,
        Arrv_Cntry_Cd,Dpt_Airpt_Cd,Dpt_Cty_Cd,Dpt_Cntry_Cd,Cls_Cd,
        Tkt_Typ_Ind,Tkt_Fmt_Typ,Tkt_Txn_Typ,Eqt_Crncy_Cd,Grp_Ind,Tour_Cd,
        sum(D_Seg_Qty) as D_Seg_Qty,sum(I_Seg_Qty) as I_Seg_Qty,
        sum(Tax_Amt) as Tax_Amt,sum(Commsn_Amt) as Commsn_Amt,
        sum(Net_Amt) as Net_Amt,sum(Tkt_Amt) as Tkt_Amt ,
        sum(Tkt_Qty) as Tkt_Qty,sum(Pax_Qty) as Pax_Qty
    FROM DSS_TTemp.STKT_AL_SELL_DAILY_AGG
    GROUP BY 1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18
    )
    WITH DATA;

    结果在第一次执行时,跑了15个多小时还没完。通过查看Explain Plan,发现该sql一直卡在merge过程中。百思不得其解,请教老员工才知道,原来是PRIMARY INDEX的问题:Teradata默认将新表的第一个字段day_id作为了主索引,由于日期取值范围比较小,导致Teradata算出的ROW HASH值重复比较多,使得数据在磁盘中的分配极不平均,主要集中在某几个AMP中,所以插入时会相当的慢。

    Teradata数据库主索引

    1. 主索引的概念
    2. 哈希值的存储方法
    3. PI对数据库查询性能的影响

    在进行Teradata数据库的逻辑设计时,对于每一个表,都要指定一个“主索引”(Primary Index,简称PI),Teradata数据库引擎会根据这个主索引的实际值,同时根据系统的配置情况(主要是AMP的个数),通过一种哈希算法,为每个表的每一条数据都生成一个“行哈希值”(Row Hash Value),Teradata会根据这个行哈希值把数据分布到某一个确定的AMP上。

     

    数据分布的过程中,在值20和30所在列上定义了Primary Index,系统的哈希算法根据20和30这两个值,生成了两个不同的行哈希值,之后系统根据这两个行哈希值的内容,把20和30各自所对应的行分别分布到了不同的AMP上进行存储了。

     

    在获取数据的时候(SELECT、UPDATE、DELETE都是获取数据的SQL操作),系统会使用与进行数据分布时相同的哈希算法对20和30进行哈希运算,这会得到相同的行哈希值,系统就根据这个行哈希值直接定位到20或者30各自所在的AMP,并由各自对应的AMP返回要获取的行。

     

    根据哈希算法,对于不同的Primary Index值,可能会计算出相同的行哈希值,这些具有相同的行哈希值的数据行就会被分布在同一个AMP上。这样,如果哈希算法选择得当,则可以基本保证,同一个表中的数据在整个Teradata并行系统的多个AMP上的分布是趋于均匀的。

     

    对于一个Teradata系统,其哈希算法是确定的,而且是运行时不可变的,在系统的硬件不变的前提下(AMP数不变),这就保证了对于同一个Primary Index值,所生成的行哈希值也是相同的。因此,对于不同的表,尤其是有主-外键关联关系的表,通过慎重地定义Primary Index,可以做到那些经常要进行关联(往往是主-外键关联)的行会被分布到同一个AMP上,这大大缩短了数据库进行数据关联的时间,提高了Teradata系统的性能。

     

  • 相关阅读:
    Could not resolve com.android.support:appcompat-v7:28.0.0 错误处理
    解决 Could not resolve com.android.tools.build:gradle:3.1.3
    https://maven.google.com 连接不上的解决办法(转)
    jquery操作select(取值,设置选中)
    django 使用 request 获取浏览器发送的参数
    jquery下载,实时更新jquery1.2到最新3.3.1所有版本下载
    myeclipse 8.5反编译插件失效
    再探java基础——对面向对象的理解(2)
    庖丁解牛FPPopover
    去大连
  • 原文地址:https://www.cnblogs.com/baiduligang/p/4247597.html
Copyright © 2011-2022 走看看