精华内容
下载资源
问答
  • 今天收到业务人员发来的工单,说是程序访问特别,问有无做过更新和更改,回答没有做过更新和其他操作。于是通过PS/SQL连接库,点击登录后发现非常。于是XSHEEL到服务器,用tnsping,ping实例名,发现无法ping通...

    今天收到业务人员发来的工单,说是程序访问特别慢,问有无做过更新和更改,回答没有做过更新和其他操作。于是通过PS/SQL连接库,点击登录后发现非常慢。于是XSHEEL到服务器,用tnsping,ping实例名,发现无法ping通,偶尔ping通延时挺高,确实不正常。

    分析:因为是单机所以不存在网络问题,查找解析是否正常
    检查/etc/hosts主机名和IP映射正确的。
    检查/etc/resolve/发现DNS里增加了一个外网DNS8.8.8.8,导致访问解析不正确,出现访问慢或者无法访问。注销8.8.8.8DNS。再次tnsping,正常。

    ps/SQL连接正常

    展开全文
  • Oracle数据库访问性能优化

    万次阅读 多人点赞 2018-02-20 16:02:36
    所有数据库包括Oracle的sql优化都是针对程序员的,而不是针对dba的,第一,尽量防止模糊,明确指出,即用列名代替*,第二,在where语句上下工夫。第三多表查询和子查询,第四尽量使用绑定。 根据计算机硬件的基本...

           所有数据库包括Oracle的sql优化都是针对程序员的,而不是针对dba的,第一,尽量防止模糊,明确指出,即用列名代替*,第二,在where语句上下工夫。第三多表查询和子查询,第四尽量使用绑定。

           根据计算机硬件的基本性能指标及其在数据库中主要操作内容,可以整理出如下图所示的性能基本优化法则:

           这个优化法则归纳为5个层次:
           1、减少数据访问(减少磁盘访问)
           2、返回更少数据(减少网络传输或磁盘访问)
           3、减少交互次数(减少网络传输)
           4、减少服务器CPU开销(减少CPU及内存开销)
           5、利用更多资源(增加资源)
           由于每一层优化法则都是解决其对应硬件的性能问题,所以带来的性能提升比例也不一样。传统数据库系统设计是也是尽可能对低速设备提供优化方法,因此针对低速设备问题的可优化手段也更多,优化成本也更低。我们任何一个SQL的性能优化都应该按这个规则由上到下来诊断问题并提出解决方案,而不应该首先想到的是增加资源解决问题。

           以下是每个优化法则层级对应优化效果及成本经验参考:

    优化法则

    性能提升效果

    优化成本

    减少数据访问

    1~1000

    返回更少数据

    1~100

    减少交互次数

    1~20

    减少服务器CPU开销

    1~5

    利用更多资源

    @~10

    1 减少数据访问

    1.1 创建并使用正确的索引

           数据库索引的原理非常简单,但在复杂的表中真正能正确使用索引的人很少,即使是专业的DBA也不一定能完全做到最优。
           索引会大大增加表记录的DML(INSERT,UPDATE,DELETE)开销,正确的索引可以让性能提升100,1000倍以上,不合理的索引也可能会让性能下降100倍,因此在一个表中创建什么样的索引需要平衡各种业务需求。
    一、SQL什么条件会使用索引?
           当字段上建有索引时,通常以下情况会使用索引:
           INDEX_COLUMN = ?
           INDEX_COLUMN > ?
           INDEX_COLUMN >= ?
           INDEX_COLUMN < ?
           INDEX_COLUMN <= ?
           INDEX_COLUMN between ? and ?
           INDEX_COLUMN in (?,?,...,?)
           INDEX_COLUMN like ?||'%'(后导模糊查询)
           T1. INDEX_COLUMN=T2. COLUMN1(两个表通过索引字段关联)

    二、SQL什么条件不会使用索引?

    查询条件

    不能使用索引原因

    INDEX_COLUMN <> ?

    INDEX_COLUMN not in (?,?,...,?)

    不等于操作不能使用索引

    function(INDEX_COLUMN) = ?

    INDEX_COLUMN + 1 = ?

    INDEX_COLUMN || 'a' = ?

    经过普通运算或函数运算后的索引字段不能使用索引

    INDEX_COLUMN like '%'||?

    INDEX_COLUMN like '%'||?||'%'

    含前导模糊查询的Like语法不能使用索引

    INDEX_COLUMN is null

    B-TREE索引里不保存字段为NULL值记录,因此IS NULL不能使用索引

    NUMBER_INDEX_COLUMN='12345'

    CHAR_INDEX_COLUMN=12345

    Oracle在做数值比较时需要将两边的数据转换成同一种数据类型,如果两边数据类型不同时会对字段

    值隐式转换,相当于加了一层函数处理,所以不能使用索引。

    a.INDEX_COLUMN=a.COLUMN_1

    给索引查询的值应是已知数据,不能是未知字段值。

    注:经过函数运算字段的字段要使用可以使用函数索引,这种需求建议与DBA沟通。

    有时候我们会使用多个字段的组合索引,如果查询条件中第一个字段不能使用索引,那整个查询也不能使用索引。

    如:我们company表建了一个id+name的组合索引,以下SQL是不能使用索引的

    Select * from company where name=?

    Oracle9i后引入了一种index skip scan的索引方式来解决类似的问题,但是通过index skip scan提高性能的条件比较特殊,使用不好反而性能会更差。

    三、我们一般在什么字段上建索引?
           这是一个非常复杂的话题,需要对业务及数据充分分析后再能得出结果。主键及外键通常都要有索引,其它需要建索引的字段应满足以下条件:
           1、字段出现在查询条件中,并且查询条件可以使用索引;
           2、语句执行频率高,一天会有几千次以上(并发测试必须有索引);
           3、通过字段条件可筛选的记录集很小,那数据筛选比例是多少才适合?
           这个没有固定值,需要根据表数据量来评估,以下是经验公式,可用于快速评估:
           小表(记录数小于10000行的表):筛选比例<10%;
           大表:(筛选返回记录数)<(表总记录数*单条记录长度)/10000/16
           单条记录长度≈字段平均内容长度之和+字段数*2

     

           以下是一些字段是否需要建B-TREE索引的经验分类:

     

     

    字段类型

    常见字段名

    需要建索引的

    字段

    主键

    ID,PK

    外键

    PRODUCT_ID,COMPANY_ID,MEMBER_ID,ORDER_ID,TRADE_ID,PAY_ID

    有对像或身份标识意义字段

    HASH_CODE,USERNAME,IDCARD_NO,EMAIL,TEL_NO,IM_NO

    索引慎用字段,

    需要进行数据

    分布及使用场

    景详细评估

    日期

    GMT_CREATE,GMT_MODIFIED

    年月

    YEAR,MONTH

    状态标志

    PRODUCT_STATUS,ORDER_STATUS,IS_DELETE,VIP_FLAG

    类型

    ORDER_TYPE,IMAGE_TYPE,GENDER,CURRENCY_TYPE

    区域

    COUNTRY,PROVINCE,CITY

    操作人员

    CREATOR,AUDITOR

    数值

    LEVEL,AMOUNT,SCORE

    长字符

    ADDRESS,COMPANY_NAME,SUMMARY,SUBJECT

    不适合建索引

    的字段

    描述备注

    DESCRIPTION,REMARK,MEMO,DETAIL

    大字段

    FILE_CONTENT,EMAIL_CONTEN

    四、如何知道SQL是否使用了正确的索引?
           简单SQL可以根据索引使用语法规则判断,复杂的SQL不好办,判断SQL的响应时间是一种策略,但是这会受到数据量、主机负载及缓存等因素的影响,有时数据全在缓存里,可能全表访问的时间比索引访问时间还少。要准确知道索引是否正确使用,需要到数据库中查看SQL真实的执行计划,这个话题比较复杂,详见SQL执行计划专题介绍。

    以下是执行计划获取方式:

     

    select SQL_TEXT,SQL_ID,OPTIMIZER_MODE,parsing_schema_name,LAST_ACTIVE_TIME from V$SQLAREA;

    select from table(dbms_xplan.display_cursor('gsyvkdr40w01r'));----gsyvkdr40w01r为SQL_ID

    五、索引对DML(INSERT,UPDATE,DELETE)附加的开销有多少?
           这个没有固定的比例,与每个表记录的大小及索引字段大小密切相关,以下是一个普通表测试数据,仅供参考:
           索引对于Insert性能降低56%
           索引对于Update性能降低47%
           索引对于Delete性能降低29%
           因此对于写IO压力比较大的系统,表的索引需要仔细评估必要性,另外索引也会占用一定的存储空间。

    1.2 只通过索引访问数据

          有些时候,我们只是访问表中的几个字段,并且字段内容较少,我们可以为这几个字段单独建立一个组合索引,这样就可以直接只通过访问索引就能得到数据,一般索引占用的磁盘空间比表小很多,所以这种方式可以大大减少磁盘IO开销。
          如:select id,name from company where type='2';
          如果这个SQL经常使用,我们可以在type,id,name上创建组合索引
          create index my_comb_index on company(type,id,name);
          有了这个组合索引后,SQL就可以直接通过my_comb_index索引返回数据,不需要访问company表。
          还是拿字典举例:有一个需求,需要查询一本汉语字典中所有汉字的个数,如果我们的字典没有目录索引,那我们只能从字典内容里一个一个字计数,最后返回结果。如果我们有一个拼音目录,那就可以只访问拼音目录的汉字进行计数。如果一本字典有1000页,拼音目录有20页,那我们的数据访问成本相当于全表访问的50分之一。

          切记,性能优化是无止境的,当性能可以满足需求时即可,不要过度优化。在实际数据库中我们不可能把每个SQL请求的字段都建在索引里,所以这种只通过索引访问数据的方法一般只用于核心应用,也就是那种对核心表访问量最高且查询字段数据量很少的查询。

    1.3 优化SQL执行计划

          SQL执行计划是关系型数据库最核心的技术之一,它表示SQL执行时的数据访问算法。由于业务需求越来越复杂,表数据量也越来越大,程序员越来越懒惰,SQL也需要支持非常复杂的业务逻辑,但SQL的性能还需要提高,因此,优秀的关系型数据库除了需要支持复杂的SQL语法及更多函数外,还需要有一套优秀的算法库来提高SQL性能。
          目前ORACLE有SQL执行计划的算法约300种,而且一直在增加,所以SQL执行计划是一个非常复杂的课题,一个普通DBA能掌握50种就很不错了,就算是资深DBA也不可能把每个执行计划的算法描述清楚。虽然有这么多种算法,但并不表示我们无法优化执行计划,因为我们常用的SQL执行计划算法也就十几个,如果一个程序员能把这十几个算法搞清楚,那就掌握了80%的SQL执行计划调优知识。

          推荐使用的SQL执行计划优化工具:Dell SQL Optimizer for Oracle

    2 返回更少的数据

    2.1 数据分页处理

    一般数据分页方式有:
    1、客户端(应用程序或浏览器)分页
          将数据从应用服务器全部下载到本地应用程序或浏览器,在应用程序或浏览器内部通过本地代码进行分页处理
          优点:编码简单,减少客户端与应用服务器网络交互次数
          缺点:首次交互时间长,占用客户端内存
          适应场景:客户端与应用服务器网络延时较大,但要求后续操作流畅,如手机GPRS,超远程访问(跨国)等等。
    2、应用服务器分页
         将数据从数据库服务器全部下载到应用服务器,在应用服务器内部再进行数据筛选。以下是一个应用服务器端Java程序分页的示例:
         List list=executeQuery(“select * from employee order by id”);
         Int count= list.size();
         List subList= list.subList(10, 20);
          优点:编码简单,只需要一次SQL交互,总数据与分页数据差不多时性能较好。
          缺点:总数据量较多时性能较差。
          适应场景:数据库系统不支持分页处理,数据量较小并且可控。
    3、数据库SQL分页
          采用数据库SQL分页需要两次SQL完成
          一个SQL计算总数量
          一个SQL返回分页后的数据
          优点:性能好
          缺点:编码复杂,各种数据库语法不同,需要两次SQL交互。
          oracle数据库一般采用rownum来进行分页,常用分页语法有如下两种:

    (1)直接通过rownum分页:

    select*from(

             select a.*,rownum rn from

                       (select*from product a where company_id=? orderby status) a

             whererownum<=20)

    where rn>10;

          数据访问开销=索引IO+索引全部记录结果对应的表数据IO
    (2)采用rowid分页语法

          优化原理是通过纯索引找出分页记录的ROWID,再通过ROWID回表返回数据,要求内层查询和排序字段全在索引里。

     

    createindex myindex on product(company_id,status);

    select b.*from(

             select*from(

                       select a.*,rownum rn from

                                (selectrowid rid,status from product a where company_id=? orderby status) a

                       whererownum<=20)

             where rn>10) a, product b

    wherea.rid=b.rowid;

           数据访问开销=索引IO+索引分页结果对应的表数据IO
           实例:
           一个公司产品有1000条记录,要分页取其中20个产品,假设访问公司索引需要50个IO,2条记录需要1个表数据IO。

     

    那么按第一种ROWNUM分页写法,需要550(50+1000/2)个IO,按第二种ROWID分页写法,只需要60个IO(50+20/2);

    2.2 只返回需要的字段

           通过去除不必要的返回字段可以提高性能,例:
           调整前:select * from product where company_id=?;
           调整后:select id,name from product where company_id=?;
           优点:
           1、减少数据在网络上传输开销
           2、减少服务器数据处理开销
           3、减少客户端内存占用
           4、字段变更时提前发现问题,减少程序BUG
           5、如果访问的所有字段刚好在一个索引里面,则可以使用纯索引访问提高性能。
           缺点:增加编码工作量
           由于会增加一些编码工作量,所以一般需求通过开发规范来要求程序员这么做,否则等项目上线后再整改工作量更大。
           如果你的查询表中有大字段或内容较多的字段,如备注信息、文件内容等等,那在查询表时一定要注意这方面的问题,否则可能会带来严重的性能问题。如果表经常要查询并且请求大内容字段的概率很低,我们可以采用分表处理,将一个大表分拆成两个一对一的关系表,将不常用的大内容字段放在一张单独的表中。如一张存储上传文件的表:
           T_FILE(ID,FILE_NAME,FILE_SIZE,FILE_TYPE,FILE_CONTENT)
           我们可以分拆成两张一对一的关系表:
           T_FILE(ID,FILE_NAME,FILE_SIZE,FILE_TYPE)
           T_FILECONTENT(ID, FILE_CONTENT)

           通过这种分拆,可以大大提少T_FILE表的单条记录及总大小,这样在查询T_FILE时性能会更好,当需要查询FILE_CONTENT字段内容时再访问T_FILECONTENT表。

    3 减少交互次数

    3.1 batch DML

           数据库访问框架一般都提供了批量提交的接口,jdbc支持batch的提交处理方法,当你一次性要往一个表中插入1000万条数据时,如果采用普通的executeUpdate处理,那么和服务器交互次数为1000万次,按每秒钟可以向数据库服务器提交10000次估算,要完成所有工作需要1000秒。如果采用批量提交模式,1000条提交一次,那么和服务器交互次数为1万次,交互次数大大减少。采用batch操作一般不会减少很多数据库服务器的物理IO,但是会大大减少客户端与服务端的交互次数,从而减少了多次发起的网络延时开销,同时也会降低数据库的CPU开销。

           假设要向一个普通表插入1000万数据,每条记录大小为1K字节,表上没有任何索引,客户端与数据库服务器网络是100Mbps,以下是根据现在一般计算机能力估算的各种batch大小性能对比值:

     单位:ms

    No batch

    Batch=10

    Batch=100

    Batch=1000

    Batch=10000

    服务器事务处理时间

    0.1

    0.1

    0.1

    0.1

    0.1

    服务器IO处理时间

    0.02

    0.2

    2

    20

    200

    网络交互发起时间

    0.1

    0.1

    0.1

    0.1

    0.1

    网络数据传输时间

    0.01

    0.1

    1

    10

    100

    小计

    0.23

    0.5

    3.2

    30.2

    300.2

    平均每条记录处理时间

    0.23

    0.05

    0.032

    0.0302

    0.03002

           从上可以看出,Insert操作加大Batch可以对性能提高近8倍性能,一般根据主键的Update或Delete操作也可能提高2-3倍性能,但不如Insert明显,因为Update及Delete操作可能有比较大的开销在物理IO访问。以上仅是理论计算值,实际情况需要根据具体环境测量。另外从测试角度来说,使用Batch也降低了并发性(毕竟Batch属于事务操作)。

    3.2 In List

           很多时候我们需要按一些ID查询数据库记录,我们可以采用一个ID一个请求发给数据库,如下所示:

           for:varin ids[] do begin

                    select*from mytable whereid=:var;

           end;
           我们也可以做一个小的优化, 如下所示,用ID INLIST的这种方式写SQL:

     

           select*frommytable whereidin(:id1,id2,...,idn);

     

           通过这样处理可以大大减少SQL请求的数量,从而提高性能。那如果有10000个ID,那是不是全部放在一条SQL里处理呢?答案肯定是否定的。首先大部份数据库都会有SQL长度和IN里个数的限制,如ORACLE的IN里就不允许超过1000个值。
           另外当前数据库一般都是采用基于成本的优化规则,当IN数量达到一定值时有可能改变SQL执行计划,从索引访问变成全表访问,这将使性能急剧变化。随着SQL中IN的里面的值个数增加,SQL的执行计划会更复杂,占用的内存将会变大,这将会增加服务器CPU及内存成本。
           评估在IN里面一次放多少个值还需要考虑应用服务器本地内存的开销,有并发访问时要计算本地数据使用周期内的并发上限,否则可能会导致内存溢出。

           综合考虑,一般IN里面的值个数超过20个以后性能基本没什么太大变化,也特别说明不要超过100,超过后可能会引起执行计划的不稳定性及增加数据库CPU及内存成本,这个需要专业DBA评估。

    3.3 设置Fetch Size

           当我们采用select从数据库查询数据时,数据默认并不是一条一条返回给客户端的,也不是一次全部返回客户端的,而是根据客户端fetch_size参数处理,每次只返回fetch_size条记录,当客户端游标遍历到尾部时再从服务端取数据,直到最后全部传送完成。所以如果我们要从服务端一次取大量数据时,可以加大fetch_size,这样可以减少结果数据传输的交互次数及服务器数据准备时间,提高性能。

           以下是jdbc测试的代码,采用本地数据库,表缓存在数据库CACHE中,因此没有网络连接及磁盘IO开销,客户端只遍历游标,不做任何处理,这样更能体现fetch参数的影响:

    String vsql ="select * from t_employee";

    PreparedStatementpstmt =conn.prepareStatement(vsql,ResultSet.TYPE_FORWARD_ONLY,ResultSet.CONCUR_READ_ONLY);

    pstmt.setFetchSize(1000);

    ResultSetrs = pstmt.executeQuery(vsql);

    int cnt = rs.getMetaData().getColumnCount();

    Object o;

    while(rs.next()) {

        for(int i =1; i <= cnt; i++) {

           o = rs.getObject(i);

        }

    }

           测试示例中的employee表有100000条记录,每条记录平均长度135字节

           以下是测试结果,对每种fetchsize测试5次再取平均值:

    etchsize

     elapse_time(s

    1

    20.516

    2

    11.34

    4

    6.894

    8

    4.65

    16

    3.584

    32

    2.865

    64

    2.656

    128

    2.44

    256

    2.765

    512

    3.075

    1024

    2.862

    2048

    2.722

    4096

    2.681

    8192

    2.715

           Oracle jdbc fetchsize默认值为10,由上测试可以看出fetchsize对性能影响还是比较大的,但是当fetchsize大于100时就基本上没有影响了。fetchsize并不会存在一个最优的固定值,因为整体性能与记录集大小及硬件平台有关。根据测试结果建议当一次性要取大量数据时这个值设置为100左右,不要小于40。注意,fetchsize不能设置太大,如果一次取出的数据大于JVM的内存会导致内存溢出,所以建议不要超过1000,太大了也没什么性能提高,反而可能会增加内存溢出的危险。

           注:图中fetchsize在128以后会有一些小的波动,这并不是测试误差,而是由于resultset填充到具体对像时间不同的原因,由于resultset已经到本地内存里了,所以估计是由于CPU的L1,L2 Cache命中率变化造成,由于变化不大,所以笔者也未深入分析原因。

    3.4 使用存储过程

           大型数据库一般都支持存储过程,合理的利用存储过程也可以提高系统性能。如你有一个业务需要将A表的数据做一些加工然后更新到B表中,但是又不可能一条SQL完成,这时你需要如下3步操作:
           a:将A表数据全部取出到客户端;
           b:计算出要更新的数据;
           c:将计算结果更新到B表。
           如果采用存储过程你可以将整个业务逻辑封装在存储过程里,然后在客户端直接调用存储过程处理,这样可以减少网络交互的成本。
           当然,存储过程也并不是十全十美,存储过程有以下缺点:
           a、不可移植性,每种数据库的内部编程语法都不太相同,当你的系统需要兼容多种数据库时最好不要用存储过程。
           b、学习成本高,DBA一般都擅长写存储过程,但并不是每个程序员都能写好存储过程,除非你的团队有较多的开发人员熟悉写存储过程,否则后期系统维护会产生问题。
           c、业务逻辑多处存在,采用存储过程后也就意味着你的系统有一些业务逻辑不是在应用程序里处理,这种架构会增加一些系统维护和调试成本。
           d、存储过程和常用应用程序语言不一样,它支持的函数及语法有可能不能满足需求,有些逻辑就只能通过应用程序处理。
           e、如果存储过程中有复杂运算的话,会增加一些数据库服务端的处理成本,对于集中式数据库可能会导致系统可扩展性问题。
           f、为了提高性能,数据库会把存储过程代码编译成中间运行代码(类似于java的class文件),所以更像静态语言。当存储过程引用的对像(表、视图等等)结构改变后,存储过程需要重新编译才能生效,在24*7高并发应用场景,一般都是在线变更结构的,所以在变更的瞬间要同时编译存储过程,这可能会导致数据库瞬间压力上升引起故障(Oracle数据库就存在这样的问题)。

           个人观点:普通业务逻辑尽量不要使用存储过程,定时性的ETL任务或报表统计函数可以根据团队资源情况采用存储过程处理。

    3.5 优化业务逻辑

           要通过优化业务逻辑来提高性能是比较困难的,这需要程序员对所访问的数据及业务流程非常清楚。

           举个例子:12306网站的春运购票压力很大,可以通过业务优化来解决部分问题,比如按客流量分散,一方面从时间上分散(允许提前两个月订票,将购买压力分散到不同时间段),另一方面按客运段分布(按省市、客户段分布售票,避免票源集中发售),还可以按需求差异分类处理(比如按T、K、G、D车型分类,一等座、二等座、硬座、卧铺分类等)。

    3.6 使用ResultSet游标处理记录

           现在大部分Java框架都是通过jdbc从数据库取出数据,然后装载到一个list里再处理,list里可能是业务Object,也可能是hashmap。
           由于JVM内存一般都小于4G,所以不可能一次通过sql把大量数据装载到list里。为了完成功能,很多程序员喜欢采用分页的方法处理,如一次从数据库取1000条记录,通过多次循环搞定,保证不会引起JVM Out of memory问题。
           很多持久层框架(如iBatis)为了尽量让程序员使用方便,封装了jdbc通过statement执行数据返回到resultset的细节,导致程序员会想采用分页的方式处理问题。实际上如果我们采用jdbc原始的resultset游标处理记录,在resultset循环读取的过程中处理记录,这样就可以一次从数据库取出所有记录。显著提高性能。

         这里需要注意的是,采用resultset游标处理记录时,应该将游标的打开方式设置为FORWARD_READONLY模式(ResultSet.TYPE_FORWARD_ONLY,ResultSet.CONCUR_READ_ONLY),否则会把结果缓存在JVM里,造成JVM Out of memory问题。以下代码示例:

    String vsql ="select * from t_employee";

    PreparedStatementpstmt =conn.prepareStatement(vsql,ResultSet.TYPE_FORWARD_ONLY,ResultSet.CONCUR_READ_ONLY);

    pstmt.setFetchSize(100);

    ResultSetrs = pstmt.executeQuery(vsql);

    int col_cnt = rs.getMetaData().getColumnCount();

    Object o;

    while(rs.next()) {

             for(int j =1; j <= col_cnt; j++) {

                       o = rs.getObject(j);

             }

    }

           以上代码实际执行时间为3.156秒,而采用分页的方法处理实际需要6.516秒。性能提高了1倍多,如果采用分页模式数据库每次还需发生磁盘IO的话那性能可以提高更多。

    4 减少数据库服务器CPU运算

    4.1 使用绑定变量

           绑定变量是指SQL中对变化的值采用变量参数的形式提交,而不是在SQL中直接拼写对应的值。
           非绑定变量写法:Select * from employee where id=1234567
           绑定变量写法:
           Select * from employee where id=?

           Preparestatement.setInt(1,1234567)

           Java中Preparestatement就是为处理绑定变量提供的对像,绑定变量有以下优点:
           1、防止SQL注入
           2、提高SQL可读性
           3、提高SQL解析性能,不使用绑定变更我们一般称为硬解析,使用绑定变量我们称为软解析。
           第1和第2点很好理解,做编码的人应该都清楚,这里不详细说明。关于第3点,到底能提高多少性能呢,下面举一个例子说明:
           假设有这个这样的一个数据库主机:
           2个4核CPU 
           100块磁盘,每个磁盘支持IOPS为160
           业务应用的SQL如下:
           select * from table where pk=?
           这个SQL平均4个IO(3个索引IO+1个数据IO)
           IO缓存命中率75%(索引全在内存中,数据需要访问磁盘)
           SQL硬解析CPU消耗:1ms  (常用经验值)

           SQL软解析CPU消耗:0.02ms(常用经验值)

           假设CPU每核性能是线性增长,访问内存Cache中的IO时间忽略,要求计算系统对如上应用采用硬解析与采用软解析支持的每秒最大并发数:

    是否使用绑定变量

    CPU支持最大并发数

    磁盘IO支持最大并发数

    不使用

    2*4*1000=8000

    100*160=16000

    使用

    2*4*1000/0.02=400000

    100*160=16000

           从以上计算可以看出,不使用绑定变量的系统当并发达到8000时会在CPU上产生瓶颈,当使用绑定变量的系统当并行达到16000时会在磁盘IO上产生瓶颈。所以如果你的系统CPU有瓶颈时请先检查是否存在大量的硬解析操作。

           使用绑定变量为何会提高SQL解析性能,这个需要从数据库SQL执行原理说明,一条SQL在Oracle数据库中的执行过程如下图所示:

           当一条SQL发送给数据库服务器后,系统首先会将SQL字符串进行hash运算,得到hash值后再从服务器内存里的SQL缓存区中进行检索,如果有相同的SQL字符,并且确认是同一逻辑的SQL语句,则从共享池缓存中取出SQL对应的执行计划,根据执行计划读取数据并返回结果给客户端。

           如果在共享池中未发现相同的SQL则根据SQL逻辑生成一条新的执行计划并保存在SQL缓存区中,然后根据执行计划读取数据并返回结果给客户端。

           为了更快的检索SQL是否在缓存区中,首先进行的是SQL字符串hash值对比,如果未找到则认为没有缓存,如果存在再进行下一步的准确对比,所以要命中SQL缓存区应保证SQL字符是完全一致,中间有大小写或空格都会认为是不同的SQL。

           如果我们不采用绑定变量,采用字符串拼接的模式生成SQL,那么每条SQL都会产生执行计划,这样会导致共享池耗尽,缓存命中率也很低。

           一些无需使用绑定变量的场景:
           a、数据仓库应用,这种应用一般并发不高,但是每个SQL执行时间很长,SQL解析的时间相比SQL执行时间比较小,绑定变量对性能提高不明显。数据仓库一般都是内部分析应用,所以也不太会发生SQL注入的安全问题。
           b、数据分布不均匀的特殊逻辑,如产品表,记录有1亿,有一产品状态字段,上面建有索引,有审核中,审核通过,审核未通过3种状态,其中审核通过9500万,审核中1万,审核不通过499万。
           要做这样一个查询:
           select count(*) from product where status=?
           采用绑定变量的话,那么只会有一个执行计划,如果走索引访问,那么对于审核中查询很快,对审核通过和审核不通过会很慢;如果不走索引,那么对于审核中与审核通过和审核不通过时间基本一样;
           对于这种情况应该不使用绑定变量,而直接采用字符拼接的方式生成SQL,这样可以为每个SQL生成不同的执行计划,如下所示。
           select count(*) from product where status='approved'; //不使用索引(审核通过)
           select count(*) from product where status='tbd'; //不使用索引(审核未通过)

           select count(*) from product where status='auditing';//使用索引(审核中)

    4.2 合理使用排序

           Oracle的排序算法一直在优化,但是总体时间复杂度约等于nLog(n)。普通OLTP系统排序操作一般都是在内存里进行的,对于数据库来说是一种CPU的消耗,曾在PC机做过测试,单核普通CPU在1秒钟可以完成100万条记录的全内存排序操作,所以说由于现在CPU的性能增强,对于普通的几十条或上百条记录排序对系统的影响也不会很大。但是当你的记录集增加到上万条以上时,你需要注意是否一定要这么做了,大记录集排序不仅增加了CPU开销,而且可能会由于内存不足发生硬盘排序的现象,当发生硬盘排序时性能会急剧下降,这种需求需要与DBA沟通再决定,取决于你的需求和数据,所以只有你自己最清楚,而不要被别人说排序很慢就吓倒。
           以下列出了可能会发生排序操作的SQL语法:
           Order by
           Group by
           Distinct
           Exists子查询
           Not Exists子查询
           In子查询
           Not In子查询
           Union(并集),Union All也是一种并集操作,但是不会发生排序,如果你确认两个数据集不需要执行去除重复数据操作,那请使用Union All 代替Union。
           Minus(差集)
           Intersect(交集)
           Create Index

           Merge Join,这是一种两个表连接的内部算法,执行时会把两个表先排序好再连接,应用于两个大表连接的操作。如果你的两个表连接的条件都是等值运算,那可以采用Hash Join来提高性能,因为Hash Join使用Hash 运算来代替排序的操作。具体原理及设置参考SQL执行计划优化专题。

    4.3 减少比较操作

           我们SQL的业务逻辑经常会包含一些比较操作,如a=b,a<b之类的操作,对于这些比较操作数据库都体现得很好,但是如果有以下操作,我们需要保持警惕:
           Like模糊查询,如下所示:
           a like ‘%abc%’
           Like模糊查询对于数据库来说不是很擅长,特别是你需要模糊检查的记录有上万条以上时,性能比较糟糕,这种情况一般可以采用专用Search或者采用全文索引方案来提高性能。
           不能使用索引定位的大量In List,如下所示:
           a in (:1,:2,:3,…,:n)   ----n>20
           如果这里的a字段不能通过索引比较,那数据库会将字段与in里面的每个值都进行比较运算,如果记录数有上万以上,会明显感觉到SQL的CPU开销加大,这个情况有两种解决方式:
           a、将in列表里面的数据放入一张中间小表,采用两个表Hash Join关联的方式处理;
           b、采用str2varList方法将字段串列表转换一个临时表处理,关于str2varList方法可以在网上直接查询,这里不详细介绍。
           以上两种解决方案都需要与中间表Hash Join的方式才能提高性能,如果采用了Nested Loop的连接方式性能会更差。

           如果发现我们的系统IO没问题但是CPU负载很高,就有可能是上面的原因,这种情况不太常见,如果遇到了最好能和DBA沟通并确认准确的原因。

    4.4 大量复杂运算在客户端处理

           什么是复杂运算,一般我认为是一秒钟CPU只能做10万次以内的运算。如含小数的对数及指数运算、三角函数、3DES及BASE64数据加密算法等等。

           如果有大量这类函数运算,尽量放在客户端处理,一般CPU每秒中也只能处理1万-10万次这样的函数运算,放在数据库内不利于高并发处理。

    5 利用更多的资源

    5.1 客户端多进程并行访问

           多进程并行访问是指在客户端创建多个进程(线程),每个进程建立一个与数据库的连接,然后同时向数据库提交访问请求。当数据库主机资源有空闲时,我们可以采用客户端多进程并行访问的方法来提高性能。如果数据库主机已经很忙时,采用多进程并行访问性能不会提高,反而可能会更慢。所以使用这种方式最好与DBA或系统管理员进行沟通后再决定是否采用。
           例如:
           我们有10000个产品ID,现在需要根据ID取出产品的详细信息,如果单线程访问,按每个IO要5ms计算,忽略主机CPU运算及网络传输时间,我们需要50s才能完成任务。如果采用5个并行访问,每个进程访问2000个ID,那么10s就有可能完成任务。
           那是不是并行数越多越好呢,开1000个并行是否只要50ms就搞定,答案肯定是否定的,当并行数超过服务器主机资源的上限时性能就不会再提高,如果再增加反而会增加主机的进程间调度成本和进程冲突机率。
           以下是一些如何设置并行数的基本建议:
           如果瓶颈在服务器主机,但是主机还有空闲资源,那么最大并行数取主机CPU核数和主机提供数据服务的磁盘数两个参数中的最小值,同时要保证主机有资源做其它任务。
           如果瓶颈在客户端处理,但是客户端还有空闲资源,那建议不要增加SQL的并行,而是用一个进程取回数据后在客户端起多个进程处理即可,进程数根据客户端CPU核数计算。
           如果瓶颈在客户端网络,那建议做数据压缩或者增加多个客户端,采用map reduce的架构处理。

           如果瓶颈在服务器网络,那需要增加服务器的网络带宽或者在服务端将数据压缩后再处理了。

    5.2 数据库并行处理

           数据库并行处理是指客户端一条SQL的请求,数据库内部自动分解成多个进程并行处理,如下图所示:

           并不是所有的SQL都可以使用并行处理,一般只有对表或索引进行全部访问时才可以使用并行。数据库表默认是不打开并行访问,所以需要指定SQL并行的提示,如下所示:
           select /*+parallel(a,4)*/ * from employee;
           并行的优点:
           使用多进程处理,充分利用数据库主机资源(CPU,IO),提高性能。
           并行的缺点:
           1、单个会话占用大量资源,影响其它会话,所以只适合在主机负载低时期使用;
           2、只能采用直接IO访问,不能利用缓存数据,所以执行前会触发将脏缓存数据写入磁盘操作。
           注:
           1、并行处理在OLTP类系统中慎用,使用不当会导致一个会话把主机资源全部占用,而正常事务得不到及时响应,所以一般只是用于数据仓库平台或大数据处理平台。
           2、一般对于百万级记录以下的小表采用并行访问性能并不能提高,反而可能会让性能更差。

    最后介绍一款Oracle基准性能测试工具swingbench

           目前网络上开源的oracle基准测试工具主要是orabm和swingbench,由于orabm不支持oracle 11g版本,所以建议使用swingben进行基准压力测试。另外,swingbench还能对rac进行测试。swingbench是UK based oracle Database Solutions group开发的一个oracle压力测试工具,好像是官方废弃的一个项目,官方页面http://dominicgiles.com/swingbench.html 上可以下载最新的软件版本。swingbench可以运行在windows和linux平台(可视化环境,基于JDK)。

    下载地址:http://www.dominicgiles.com/downloads.html
    作者博客:http://www.dominicgiles.com/blog/blog.html
    文档地址:http://www.dominicgiles.com/Swingbench.pdf

    展开全文
  • oracle 查询的原因总结

    千次阅读 2016-10-27 10:45:31
    查询速度的原因多,常见如下几种:    1、没有索引或者没有用到索引(这是查询最常见的问题,是程序设计的缺陷)    2、I/O吞吐量小,形成了瓶颈效应。    3、没有创建计算列导致查询不优化。   ...
    查询速度慢的原因很多,常见如下几种:
      
      1、没有索引或者没有用到索引(这是查询慢最常见的问题,是程序设计的缺陷)
      
      2、I/O吞吐量小,形成了瓶颈效应。
      
      3、没有创建计算列导致查询不优化。
      
      4、内存不足
      
      5、网络速度慢
      
      6、查询出的数据量过大(可以采用多次查询,其他的方法降低数据量)
      
      7、锁或者死锁(这也是查询慢最常见的问题,是程序设计的缺陷)
      
      8、sp_lock,sp_who,活动的用户查看,原因是读写竞争资源。
      
      9、返回了不必要的行和列
      
      10、查询语句不好,没有优化

      可以通过如下方法来优化查询 :
      
      1、把数据、日志、索引放到不同的I/O设备上,增加读取速度,以前可以将Tempdb应放在RAID0上,SQL2000不在支持。数据量(尺寸)越大,提高I/O越重要.
      
      2、纵向、横向分割表,减少表的尺寸(sp_spaceuse)
      
      3、升级硬件
      
      4、根据查询条件,建立索引,优化索引、优化访问方式,限制结果集的数据量。注意填充因子要适当(最好是使用默认值0)。索引应该尽量小,使用字节数小的列建索引好(参照索引的创建),不要对有限的几个值的字段建单一索引如性别字段
      
      5、提高网速;
      
      6、扩大服务器的内存,Windows 2000和SQL server 2000能支持4-8G的内存。配置虚拟内存:虚拟内存大小应基于计算机上并发运行的服务进行配置。运行 Microsoft SQL Server? 2000 时,可考虑将虚拟内存大小设置为计算机中安装的物理内存的 1.5 倍。如果另外安装了全文检索功能,并打算运行 Microsoft 搜索服务以便执行全文索引和查询,可考虑:将虚拟内存大小配置为至少是计算机中安装的物理内存的 3 倍。将 SQL Server max server memory 服务器配置选项配置为物理内存的 1.5 倍(虚拟内存大小设置的一半)。
      
      7、增加服务器 CPU个数;但是必须明白并行处理串行处理更需要资源例如内存。使用并行还是串行程是MsSQL自动评估选择的。单个任务分解成多个任务,就可以在处理器上运行。例如耽搁查询的排序、连接、扫描和GROUP BY字句同时执行,SQL SERVER根据系统的负载情况决定最优的并行等级,复杂的需要消耗大量的CPU的查询最适合并行处理。但是更新操作Update,Insert, Delete还不能并行处理。
      
      8、如果是使用like进行查询的话,简单的使用index是不行的,但是全文索引,耗空间。 like 'a%' 使用索引 like '%a' 不使用索引用 like '%a%' 查询时,查询耗时和字段值总长度成正比,所以不能用CHAR类型,而是VARCHAR。对于字段的值很长的建全文索引。
      
      9、DB Server 和APPLication Server 分离;OLTP和OLAP分离
      
      10、分布式分区视图可用于实现数据库服务器联合体。联合体是一组分开管理的服务器,但它们相互协作分担系统的处理负荷。这种通过分区数据形成数据库服务器联合体的机制能够扩大一组服务器,以支持大型的多层 Web 站点的处理需要。有关更多信息,参见设计联合数据库服务器。(参照SQL帮助文件'分区视图')
      
      a、在实现分区视图之前,必须先水平分区表
      
      b、在创建成员表后,在每个成员服务器上定义一个分布式分区视图,并且每个视图具有相同的名称。这样,引用分布式分区视图名的查询可以在任何一个成员服务器上运行。系统操作如同每个成员服务器上都有一个原始表的复本一样,但其实每个服务器上只有一个成员表和一个分布式分区视图。数据的位置对应用程序是透明的。
      
      11、重建索引 DBCC REINDEX ,DBCC INDEXDEFRAG,收缩数据和日志 DBCC SHRINKDB,DBCC SHRINKFILE. 设置自动收缩日志.对于大的数据库不要设置数据库自动增长,它会降低服务器的性能。在T-sql的写法上有很大的讲究,下面列出常见的要点:首先, DBMS处理查询计划的过程是这样的:
      
      1、 查询语句的词法、语法检查
      
      2、 将语句提交给DBMS的查询优化器
      
      3、 优化器做代数优化和存取路径的优化
      
      4、 由预编译模块生成查询规划
      
      5、 然后在合适的时间提交给系统处理执行
      
      6、 最后将执行结果返回给用户其次,看一下SQL SERVER的数据存放的结构:一个页面的大小为8K(8060)字节,8个页面为一个盘区,按照B树存放。
      
      12、Commit和rollback的区别 Rollback:回滚所有的事物。 Commit:提交当前的事物. 没有必要在动态SQL里写事物,如果要写请写在外面如: begin tran exec(@s) commit trans 或者将动态SQL 写成函数或者存储过程。
      
      13、在查询Select语句中用Where字句限制返回的行数,避免表扫描,如果返回不必要的数据,浪费了服务器的I/O资源,加重了网络的负担降低性能。如果表很大,在表扫描的期间将表锁住,禁止其他的联接访问表,后果严重。
      
      14、SQL的注释申明对执行没有任何影响
      15、尽可能不使用光标,它占用大量的资源。如果需要row-by-row地执行,尽量采用非光标技术,如:在客户端循环,用临时表,Table变量,用子查询,用Case语句等等。游标可以按照它所支持的提取选项进行分类: 只进 必须按照从第一行到最后一行的顺序提取行。FETCH NEXT 是唯一允许的提取操作,也是默认方式。可滚动性可以在游标中任何地方随机提取任意行。游标的技术在SQL2000下变得功能很强大,他的目的是支持循环。有四个并发选项 READ_ONLY:不允许通过游标定位更新(Update),且在组成结果集的行中没有锁。 OPTIMISTIC WITH valueS:乐观并发控制是事务控制理论的一个标准部分。乐观并发控制用于这样的情形,即在打开游标及更新行的间隔中,只有很小的机会让第二个用户更新某一行。当某个游标以此选项打开时,没有锁控制其中的行,这将有助于最大化其处理能力。如果用户试图修改某一行,则此行的当前值会与最后一次提取此行时获取的值进行比较。如果任何值发生改变,则服务器就会知道其他人已更新了此行,并会返回一个错误。如果值是一样的,服务器就执行修改。选择这个并发选项?OPTIMISTIC WITH ROW VERSIONING:此乐观并发控制选项基于行版本控制。使用行版本控制,其中的表必须具有某种版本标识符,服务器可用它来确定该行在读入游标后是否有所更改。在 SQL Server 中,这个性能由 timestamp 数据类型提供,它是一个二进制数字,表示数据库中更改的相对顺序。每个数据库都有一个全局当前时间戳值:@@DBTS。每次以任何方式更改带有 timestamp 列的行时,SQL Server 先在时间戳列中存储当前的 @@DBTS 值,然后增加 @@DBTS 的值。如果某 个表具有 timestamp 列,则时间戳会被记到行级。服务器就可以比较某行的当前时间戳值和上次提取时所存储的时间戳值,从而确定该行是否已更新。服务器不必比较所有列的值,只需比较 timestamp 列即可。如果应用程序对没有 timestamp 列的表要求基于行版本控制的乐观并发,则游标默认为基于数值的乐观并发控制。 SCROLL LOCKS 这个选项实现悲观并发控制。在悲观并发控制中,在把数据库的行读入游标结果集时,应用程序将试图锁定数据库行。在使用服务器游标时,将行读入游标时会在其上放置一个更新锁。如果在事务内打开游标,则该事务更新锁将一直保持到事务被提交或回滚;当提取下一行时,将除去游标锁。如果在事务外打开游标,则提取下一行时,锁就被丢弃。因此,每当用户需要完全的悲观并发控制时,游标都应在事务内打开。更新锁将阻止任何其它任务获取更新锁或排它锁,从而阻止其它任务更新该行。然而,更新锁并不阻止共享锁,所以它不会阻止其它任务读取行,除非第二个任务也在要求带更新锁的读取。滚动锁根据在游标定义的 Select 语句中指定的锁提示,这些游标并发选项可以生成滚动锁。滚动锁在提取时在每行上获取,并保持到下次提取或者游标关闭,以先发生者为准。下次提取时,服务器为新提取中的行获取滚动锁,并释放上次提取中行的滚动锁。滚动锁独立于事务锁,并可以保持到一个提交或回滚操作之后。如果提交时关闭游标的选项为关,则 COMMIT 语句并不关闭任何打开的游标,而且滚动锁被保留到提交之后,以维护对所提取数据的隔离。所获取滚动锁的类型取决于游标并发选项和游标 Select 语句中的锁提示。锁提示 只读 乐观数值 乐观行版本控制 锁定无提示 未锁定 未锁定 未锁定 更新 NOLOCK 未锁定未锁定未锁定 未锁定 HOLDLOCK 共享 共享 共享 更新 UPDLOCK 错误 更新 更新 更新 TABLOCKX 错误 未锁定未锁定更新其它 未锁定 未锁定 未锁定 更新 *指定 NOLOCK 提示将使指定了该提示的表在游标内是只读的。
      
      16、用Profiler来跟踪查询,得到查询所需的时间,找出SQL的问题所在;用索引优化器优化索引
      
      17、注意UNion和UNion all 的区别。UNION all好
      
      18、注意使用DISTINCT,在没有必要时不要用,它同UNION一样会使查询变慢。重复的记录在查询里是没有问题的
      
      19、查询时不要返回不需要的行、列
      
      20、用sp_configure 'query governor cost limit'或者SET QUERY_GOVERNOR_COST_LIMIT来限制查询消耗的资源。当评估查询消耗的资源超出限制时,服务器自动取消查询,在查询之前就扼杀掉。 SET LOCKTIME设置锁的时间
      
      21、用select top 100 / 10 Percent 来限制用户返回的行数或者SET ROWCOUNT来限制操作的行
      
      22、在SQL2000以前,一般不要用如下的字句: "IS NULL", "<>", "!=", "!>", "!<", "NOT", "NOT EXISTS", "NOT IN", "NOT LIKE", and "LIKE '%500'",因为他们不走索引全是表扫描。也不要在Where字句中的列名加函数,如Convert,substring等,如果必须用函数的时候,创建计算列再创建索引来替代.还可以变通写法:Where SUBSTRING(firstname,1,1) = 'm'改为Where firstname like 'm%'(索引扫描),一定要将函数和列名分开。并且索引不能建得太多和太大。NOT IN会多次扫描表,使用EXISTS、NOT EXISTS ,IN , LEFT OUTER JOIN 来替代,特别是左连接,而Exists比IN更快,最慢的是NOT操作.如果列的值含有空,以前它的索引不起作用,现在2000的优化器能够处理了。相同的是IS NULL,"NOT", "NOT EXISTS", "NOT IN"能优化她,而"<>"等还是不能优化,用不到索引。
      
      23、使用Query Analyzer,查看SQL语句的查询计划和评估分析是否是优化的SQL。一般的20%的代码占据了80%的资源,我们优化的重点是这些慢的地方。
      
      24、如果使用了IN或者OR等时发现查询没有走索引,使用显示申明指定索引: Select * FROM PersonMember (INDEX = IX_Title) Where processid IN ('男','女')
      
      25、将需要查询的结果预先计算好放在表中,查询的时候再Select。这在SQL7.0以前是最重要的手段。例如医院的住院费计算。
      
      26、MIN() 和 MAX()能使用到合适的索引。
      
      27、数据库有一个原则是代码离数据越近越好,所以优先选择Default,依次为Rules,Triggers, Constraint(约束如外健主健CheckUNIQUE……,数据类型的最大长度等等都是约束),Procedure.这样不仅维护工作小,编写程序质量高,并且执行的速度快。
      
      28、如果要插入大的二进制值到Image列,使用存储过程,千万不要用内嵌Insert来插入 (不知JAVA是否)。因为这样应用程序首先将二进制值转换成字符串(尺寸是它的两倍),服务器受到字符后又将他转换成二进制值.存储过程就没有这些动作: 方法:Create procedure p_insert as insert into table(Fimage) values (@image), 在前台调用这个存储过程传入二进制参数,这样处理速度明显改善。
      
      29、Between在某些时候比IN 速度更快,Between能够更快地根据索引找到范围。用查询优化器可见到差别。 select * from chineseresume where title in ('男','女') Select * from chineseresume where between '男' and '女' 是一样的。由于in会在比较多次,所以有时会慢些。
      
      30、在必要是对全局或者局部临时表创建索引,有时能够提高速度,但不是一定会这样,因为索引也耗费大量的资源。他的创建同是实际表一样。
      
      31、不要建没有作用的事物例如产生报表时,浪费资源。只有在必要使用事物时使用它。
      
      32、用OR的字句可以分解成多个查询,并且通过UNION 连接多个查询。他们的速度只同是否使用索引有关,如果查询需要用到联合索引,用UNION all执行的效率更高.多个OR的字句没有用到索引,改写成UNION的形式再试图与索引匹配。一个关键的问题是否用到索引。
      
       33、尽量少用视图,它的效率低。对视图操作比直接对表操作慢,可以用stored procedure来代替她。特别的是不要用视图嵌套,嵌套视图增加了寻找原始资料的难度。我们看视图的本质:它是存放在服务器上的被优化好了的已经产生了查询规划的SQL。对单个表检索数据时,不要使用指向多个表的视图,直接从表检索或者仅仅包含这个表的视图上读,否则增加了不必要的开销,查询受到干扰.为了加快视图的查询,MsSQL增加了视图索引的功能。
      
      34、没有必要时不要用DISTINCT和ORDER BY,这些动作可以改在客户端执行。它们增加了额外的开销。这同UNION 和UNION ALL一样的道理。
      
      select top 20 ad.companyname,comid,position,ad.referenceid,worklocation, convert(varchar(10),ad.postDate,120) as postDate1,workyear,degreedescription FROM jobcn_query.dbo.COMPANYAD_query ad where referenceID in('JCNAD00329667','JCNAD132168','JCNAD00337748','JCNAD00338345',
      'JCNAD00333138','JCNAD00303570','JCNAD00303569',
      'JCNAD00303568','JCNAD00306698','JCNAD00231935','JCNAD00231933',
      'JCNAD00254567','JCNAD00254585','JCNAD00254608',
      'JCNAD00254607','JCNAD00258524','JCNAD00332133','JCNAD00268618',
      'JCNAD00279196','JCNAD00268613') order by postdate desc
      
      35、在IN后面值的列表中,将出现最频繁的值放在最前面,出现得最少的放在最后面,减少判断的次数。
      
      36、当用Select INTO时,它会锁住系统表(sysobjects,sysindexes等等),阻塞其他的连接的存取。创建临时表时用显示申明语句,而不是 select INTO. drop table t_lxh begin tran select * into t_lxh from chineseresume where --commit 在另一个连接中Select * from sysobjects可以看到 Select INTO 会锁住系统表,Create table 也会锁系统表(不管是临时表还是系统表)。所以千万不要在事物内使用它!!!这样的话如果是经常要用的临时表请使用实表,或者临时表变量。
      
      37、一般在GROUP BY 个HAVING字句之前就能剔除多余的行,所以尽量不要用它们来做剔除行的工作。他们的执行顺序应该如下最优:select 的Where字句选择所有合适的行,Group By用来分组个统计行,Having字句用来剔除多余的分组。这样Group By 个Having的开销小,查询快.对于大的数据行进行分组和Having十分消耗资源。如果Group BY的目的不包括计算,只是分组,那么用Distinct更快
      
      38、一次更新多条记录比分多次更新每次一条快,就是说批处理好
      
      39、少用临时表,尽量用结果集和Table类性的变量来代替它,Table 类型的变量比临时表好
      
      40、在SQL2000下,计算字段是可以索引的,需要满足的条件如下:
      
      a、计算字段的表达是确定的
      
      b、不能用在TEXT,Ntext,Image数据类型
      
      c、必须配制如下选项 ANSI_NULLS = ON, ANSI_PADDINGS = ON, …….
      
      41、尽量将数据的处理工作放在服务器上,减少网络的开销,如使用存储过程。存储过程是编译好、优化过、并且被组织到一个执行规划里、且存储在数据库中的SQL语句,是控制流语言的集合,速度当然快。反复执行的动态SQL,可以使用临时存储过程,该过程(临时表)被放在Tempdb中。以前由于SQL SERVER对复杂的数学计算不支持,所以不得不将这个工作放在其他的层上而增加网络的开销。SQL2000支持UDFs,现在支持复杂的数学计算,函数的返回值不要太大,这样的开销很大。用户自定义函数象光标一样执行的消耗大量的资源,如果返回大的结果采用存储过程
      
      42、不要在一句话里再三的使用相同的函数,浪费资源,将结果放在变量里再调用更快
      
      43、Select COUNT(*)的效率教低,尽量变通他的写法,而EXISTS快.同时请注意区别: select count(Field of null) from Table 和 select count(Field of NOT null) from Table 的返回值是不同的!!!
      
      44、当服务器的内存够多时,配制线程数量 = 最大连接数+5,这样能发挥最大的效率;否则使用 配制线程数量<最大连接数启用SQL SERVER的线程池来解决,如果还是数量 = 最大连接数+5,严重的损害服务器的性能。
      
      45、按照一定的次序来访问你的表。如果你先锁住表A,再锁住表B,那么在所有的存储过程中都要按照这个顺序来锁定它们。如果你(不经意的)某个存储过程中先锁定表B,再锁定表A,这可能就会导致一个死锁。如果锁定顺序没有被预先详细的设计好,死锁很难被发现
      
      46、通过SQL Server Performance Monitor监视相应硬件的负载 Memory: Page Faults / sec计数器如果该值偶尔走高,表明当时有线程竞争内存。如果持续很高,则内存可能是瓶颈。
      Process:
      
      1、% DPC Time 指在范例间隔期间处理器用在缓延程序调用(DPC)接收和提供服务的百分比。(DPC 正在运行的为比标准间隔优先权低的间隔)。 由于 DPC 是以特权模式执行的,DPC 时间的百分比为特权时间百分比的一部分。这些时间单独计算并且不属于间隔计算总数的一部 分。这个总数显示了作为实例时间百分比的平均忙时。
      
      2、%Processor Time计数器 如果该参数值持续超过95%,表明瓶颈是CPU。可以考虑增加一个处理器或换一个更快的处理器。
      
      3、% Privileged Time 指非闲置处理器时间用于特权模式的百分比。(特权模式是为操作系统组件和操纵硬件驱动程序而设计的一种处理模式。它允许直接访问硬件和所有内存。另一种模式为用户模式,它是一种为应用程序、环境分系统和整数分系统设计的一种有限处理模式。操作系统将应用程序线程转换成特权模式以访问操作系统服务)。特权时间的 % 包括为间断和 DPC 提供服务的时间。特权时间比率高可能是由于失败设备产生的大数量的间隔而引起的。这个计数器将平均忙时作为样本时间的一部分显示。
      
      4、% User Time表示耗费CPU的数据库操作,如排序,执行aggregate functions等。如果该值很高,可考虑增加索引,尽量使用简单的表联接,水平分割大表格等方法来降低该值。 Physical Disk: Curretn Disk Queue Length计数器该值应不超过磁盘数的1.5~2倍。要提高性能,可增加磁盘。 SQLServer:Cache Hit Ratio计数器该值越高越好。如果持续低于80%,应考虑增加内存。 注意该参数值是从SQL Server启动后,就一直累加记数,所以运行经过一段时间后,该值将不能反映系统当前值。
      
      47、分析select emp_name form employee where salary > 3000 在此语句中若salary是Float类型的,则优化器对其进行优化为Convert(float,3000),因为3000是个整数,我们应在编程时使用3000.0而不要等运行时让DBMS进行转化。同样字符和整型数据的转换。
      
      48、查询的关联同写的顺序
      
      select a.personMemberID, * from chineseresume a,personmember b where personMemberID = b.referenceid and a.personMemberID = 'JCNPRH39681' (A = B ,B = '号码')
      
      select a.personMemberID, * from chineseresume a,personmember b where a.personMemberID = b.referenceid and a.personMemberID = 'JCNPRH39681' and b.referenceid = 'JCNPRH39681' (A = B ,B = '号码', A = '号码')
      
      select a.personMemberID, * from chineseresume a,personmember b where b.referenceid = 'JCNPRH39681' and a.personMemberID = 'JCNPRH39681' (B = '号码', A = '号码')
      
      49、
      
      (1)IF 没有输入负责人代码 THEN code1=0 code2=9999 ELSE code1=code2=负责人代码 END IF 执行SQL语句为: Select 负责人名 FROM P2000 Where 负责人代码>=:code1 AND负责人代码 <=:code2
      
      (2)IF 没有输入负责人代码 THEN  Select 负责人名 FROM P2000 ELSE code= 负责人代码 Select 负责人代码 FROM P2000 Where 负责人代码=:code END IF 第一种方法只用了一条SQL语句,第二种方法用了两条SQL语句。在没有输入负责人代码时,第二种方法显然比第一种方法执行效率高,因为它没有限制条件; 在输入了负责人代码时,第二种方法仍然比第一种方法效率高,不仅是少了一个限制条件,还因相等运算是最快的查询运算。我们写程序不要怕麻烦
      
      50、关于JOBCN现在查询分页的新方法(如下),用性能优化器分析性能的瓶颈,如果在I/O或者网络的速度上,如下的方法优化切实有效,如果在CPU或者内存上,用现在的方法更好。请区分如下的方法,说明索引越小越好。
      
      begin
      
      DECLARE @local_variable table (FID int identity(1,1),ReferenceID varchar(20))
      
      insert into @local_variable (ReferenceID)
      
      select top 100000 ReferenceID from chineseresume order by ReferenceID
      
      select * from @local_variable where Fid > 40 and fid <= 60
      
      end 和
      
      begin
      
      DECLARE @local_variable table (FID int identity(1,1),ReferenceID varchar(20))
      
      insert into @local_variable (ReferenceID)
      
      select top 100000 ReferenceID from chineseresume order by updatedate
      
      select * from @local_variable where Fid > 40 and fid <= 60
      
      end 的不同
      
      begin
      
      create table #temp (FID int identity(1,1),ReferenceID varchar(20))
      
      insert into #temp (ReferenceID)
      
      select top 100000 ReferenceID from chineseresume order by updatedate
      
      select * from #temp where Fid > 40 and fid <= 60 drop table #temp
      
      end

    另附:存储过程编写经验和优化措施  From:网页教学网

      一、适合读者对象:数据库开发程序员,数据库的数据量很多,涉及到对SP(存储过程)的优化的项目开发人员,对数据库有浓厚兴趣的人。  

      二、介绍:在数据库的开发过程中,经常会遇到复杂的业务逻辑和对数据库的操作,这个时候就会用SP来封装数据库操作。如果项目的SP较多,书写又没有一定的规范,将会影响以后的系统维护困难和大SP逻辑的难以理解,另外如果数据库的数据量大或者项目对SP 的性能要求很,就会遇到优化的问题,否则速度有可能很慢,经过亲身经验,一个经过优化过的SP要比一个性能差的SP的效率甚至高几百倍。  

      三、内容:  

      1、开发人员如果用到其他库的Table或View,务必在当前库中建立View来实现跨库操作,最好不要直接使用“databse.dbo.table_name”,因为sp_depends不能显示出该SP所使用的跨库table或view,不方便校验。  

      2、开发人员在提交SP前,必须已经使用set showplan on分析过查询计划,做过自身的查询优化检查。  

      3、高程序运行效率,优化应用程序,在SP编写过程中应该注意以下几点:   

      a)SQL的使用规范:

       i. 尽量避免大事务操作,慎用holdlock子句,提高系统并发能力。

       ii. 尽量避免反复访问同一张或几张表,尤其是数据量较大的表,可以考虑先根据条件提取数据到临时表中,然后再做连接。

       iii. 尽量避免使用游标,因为游标的效率较差,如果游标操作的数据超过1万行,那么就应该改写;如果使用了游标,就要尽量避免在游标循环中再进行表连接的操作。

       iv. 注意where字句写法,必须考虑语句顺序,应该根据索引顺序、范围大小来确定条件子句的前后顺序,尽可能的让字段顺序与索引顺序相一致,范围从大到小。

       v. 不要在where子句中的“=”左边进行函数、算术运算或其他表达式运算,否则系统将可能无法正确使用索引。

       vi. 尽量使用exists代替select count(1)来判断是否存在记录,count函数只有在统计表中所有行数时使用,而且count(1)比count(*)更有效率。

       vii. 尽量使用“>=”,不要使用“>”。

       viii. 注意一些or子句和union子句之间的替换

       ix. 注意表之间连接的数据类型,避免不同类型数据之间的连接。

       x. 注意存储过程中参数和数据类型的关系。

       xi. 注意insert、update操作的数据量,防止与其他应用冲突。如果数据量超过200个数据页面(400k),那么系统将会进行锁升级,页级锁会升级成表级锁。   

      b)索引的使用规范:

       i. 索引的创建要与应用结合考虑,建议大的OLTP表不要超过6个索引。

       ii. 尽可能的使用索引字段作为查询条件,尤其是聚簇索引,必要时可以通过index index_name来强制指定索引

       iii. 避免对大表查询时进行table scan,必要时考虑新建索引。

       iv. 在使用索引字段作为条件时,如果该索引是联合索引,那么必须使用到该索引中的第一个字段作为条件时才能保证系统使用该索引,否则该索引将不会被使用。

       v. 要注意索引的维护,周期性重建索引,重新编译存储过程。  

      c)tempdb的使用规范:

       i. 尽量避免使用distinct、order by、group by、having、join、cumpute,因为这些语句会加重tempdb的负担。

       ii. 避免频繁创建和删除临时表,减少系统表资源的消耗。

       iii. 在新建临时表时,如果一次性插入数据量很大,那么可以使用select into代替create table,避免log,提高速度;如果数据量不大,为了缓和系统表的资源,建议先create table,然后insert。

       iv. 如果临时表的数据量较大,需要建立索引,那么应该将创建临时表和建立索引的过程放在单独一个子存储过程中,这样才能保证系统能够很好的使用到该临时表的索引。

        v. 如果使用到了临时表,在存储过程的最后务必将所有的临时表显式删除,先truncate table,然后drop table,这样可以避免系统表的较长时间锁定。

        vi. 慎用大的临时表与其他大表的连接查询和修改,减低系统表负担,因为这种操作会在一条语句中多次使用tempdb的系统表。  

      d)合理的算法使用:   

      根据上面已提到的SQL优化技术和ASE Tuning手册中的SQL优化内容,结合实际应用,采用多种算法进行比较,以获得消耗资源最少、效率最高的方法。具体可用ASE调优命令:set statistics io on, set statistics time on , set showplan on 等。



    转自:http://blog.chinaunix.net/uid-10951-id-1762435.html

    展开全文
  • 公司开发的产品基本上都使用ORACLE数据库,而且业务系统中存储和使用的数据量大,使用业务系统的用户也多。在系统忙时,大约会有一千个用户同事访问数据库系统,因此经常会有用户抱怨系统,点击查询后,系统...
     
    


    公司开发的产品基本上都使用ORACLE数据库,而且业务系统中存储和使用的数据量很大,使用业务系统的用户也很多。在系统忙时,大约会有一千个用户同事访问数据库系统,因此经常会有用户抱怨系统慢,点击查询后,系统出现假死机现象,后台运行ORACLE系统的小型机的IDLE值偏低(甚至出现IDLE为0的情况,这时用户会惊呼数据库系统会瘫掉,虽然小型型机在IDLE值为0的情况下也不一定会瘫机,但这无疑会增加用户的担忧),系统运行在一个不安全的状态等等。

    对于我现在所做的ORACLE优化,其实还停留在SQL优化的层次(以前我的前辈曾给我说关于数据库优化的三个层次:一是针对SQL的优化,如使用正确是索引,使用ORACLE提示等;二是针对数据库对象的优化,如增加索引,微调表结构等;三针对业务的优化,需要更改业务逻辑或者表结果,此类优化一般代价比较大,一般很少针对正在运行的系统做类似的操作)。

    公司的客户很多,大多数情况会在公司远程处理客户的数据库问题。作为问题的定位者,一定要搞清楚实际运行的数据库系统到底出现了什么问题。现场的维护人员和用户最喜欢使用的形容词是:系统很慢;数据库锁表了等等。用户向外面传达的信心往往是非常模糊的,在开始接触这个问题时候起,我们就要引导用户去帮外面了解系统真实的情况。有几个东西是一定要看看的,一个是ORACLE系统的警告日志文件,在系统运行的有问题或者是忙时的几份STATSPACK报告(一般间隔时间10到15分钟),UNIX下SAR命令的输入结果(该命令可以按既定的时间间隔收集小型机系统CPU的使用情况)。通过这三个从现场收集的结果,我们基本可以了解现场数据库的运行情况。

    其中ORACLE系统的警告日志文件能让我们了解ORACLE系统运行有没有一些重大的问题。

    STATSPACK报告中概括了数据库系统的运行基本情况,其中关于如何解读报告可以写一本书了,不过我们首先要关注的是报告中有一段“Top 5 Timed Events”,这一段描述了当前ORACLE主要的等待事件是什么(关于ORACLE等待事件的概念可以参考相关的资料)。

    SAR命令的输入我们要关注三个输出的分布情况USR、WIO、IDLE。其中SYS+USR+WIO+IDLE应该等于100%,USR占的比例高,一般说明SQL语句执行效率有问题,这种问题一般是由于索引选择性不高、表连接顺序和方式不对等等;WIO高一般说明SQL语句频繁进行I/O操作。对于具体的问题,则需要对具体的SQL语句进行分析,在分析过程中,阅读执行计划是我们的一个重要的工具。

    在对ORACLE系统的整体情况有了一定的了解之后,下一步需要分析的就是系统运行过程效率不高的SQL,这是对业务优化的一个起点。如果这时不能够在实际系统中操作,了解SQL的运行过程是一个比较费时的过程的。不管怎么样,对于我们怀疑有问题的SQL,首先要阅读的就是该SQL的在实际系统中的执行计划,语句涉及到的表的数据量,访问表使用索引的选择性如何,表连接的顺序,多表之间的关联关系等等。

    对于ORACLE应用系统的优化,大方向上有一个顺序,首先考虑优化业务系统、再考虑优化ORACLE系统本身的参数(如内存分配等),再考虑操作系统本身的优化;在优化业务系统中,首先是首先相关的SQL,以SQL入手分析表是否缺少索引,表连接顺序是否正确,使用的索引是否正确等,然后再考虑调整表结构,调整业务逻辑等等。因此,SQL语句是我们对一个ORACLE业务系统进行优化的敲门砖。

    对于SQL优化,前面提到了,ORACLE的执行计划是我们必须使用的工具。本来按ORACLE系统本身提供的方法获取执行计划是一件非常麻烦的事情,不过现在的可视化工具比如PL/SQL DEVELOP或者TOAD等都给我们提供了非常方便的手段来获取SQL语句的执行计划,不过我认为ORACLE本身提供的方法还是有必要会的,特别是在远程处理问题的时候(我也不会,一定要学习一下)。

    获取有性能问题的SQL语句,我们主要有两个途径,一个是通过STATSPACK报告。报告中有两节是我们需要重点关注的:《SQL ordered by Gets for》和《SQL ordered by Reads for DB》,这两节中分别按语句读取内存数据库块和读取的物理数据库块(数据库块是指ORACLE的块大小,一般是操作系统最小块的整数倍)的数量倒序排列,如果其中的语句不全(太长),可通过HASH_VALUE值到ORACLE的动态视图V$SQLTEXT中获取该SQL的全部语句。第二个是通过ORACLE系统的动态视图,V$SQL,该视图记录了每个SQL语句的执行次数,物理读和内存读、执行时间等等很多SQL语句的执行信息,可以通过如下语句选择一下物理读和内存读较高的语句: SELECT

    t.HASH_VALUE,

    t.EXECUTIONS,

    t.DISK_READS,

    round(t.DISK_READS/t.EXECUTIONS) AS perDiskReads,

    t.BUFFER_GETS,

    round(t.BUFFER_GETS/t.EXECUTIONS) AS perBufferReads,

    t.ELAPSED_TIME,

    round(t.ELAPSED_TIME/t.EXECUTIONS) AS perElayTime,

    t.CPU_TIME,

    round(t.CPU_TIME/t.EXECUTIONS) AS perCpuTime,

    t.FIRST_LOAD_TIME,

    t.SQL_TEXT

    FROM v$sql t

    WHERE (t.DISK_READS/t.EXECUTIONS > 500 OR t.BUFFER_GETS/t.EXECUTIONS > 20000)

    AND t.EXECUTIONS > 0

    ORDER BY 6 DESC;


    这个语句查询出来的SQL可能也不全,也可以通过HASH_VALUE在V$SQLTEXT中找到其全部的SQL。

    对于找到的SQL语句我们可以逐一分析其执行计划,结合涉及到的表的数据量,我们可以估算或者测试该语句的执行效率,分析表WHERE条件中涉及的字段(术语叫做谓词),该字段数据分布如何,选择性是否好,是否有索引。这是一个非常繁杂和琐碎的工作,但从这些琐碎的工作中,我们能发现那些SQL执行时选择的索引不对,哪些表缺少相应的索引导致了全表扫描,哪些语句条件不够导致对分区表进行了全表扫描。总之,对于一个给定的SQL,我们结合其表数据量的大小和分布,SQL中使用的查询条件,能够找到一个性能最优的执行方式,通过调整索引、使用ORACLE提示,使ORACLE系统按照最优的方式来执行SQL。如何去分析和确定ORACLE的执行方式,一个最普遍的原则就是尽量根据其谓词(查询条件),使用选择性最好的索引(当然,对于一些小表,可以考虑使用全表扫描的方式性能会更好)。对于SQL的执行方式,需要在工作中不断积累经验,比如曾经在一次优化中发现对一个表安三个字段查询的非常多,因此决定建立该三个字段的复合索引,但结果其语句执行效率却更差。

    展开全文
  • 公司开发的产品基本上都使用ORACLE数据库,而且业务系统中存贮和使用的数据量大,使用业务系统的用户也多。在系统忙时,大约会有一千个用户同事访问数据库系统,因此经常会有用户抱怨系统,点击查询后,系统...
  • 在系统忙时,大约会有一千个用户同事访问数据库系统,因此经常会有用户抱怨系统,点击查询后,系统出现假死机现象,后台运行ORACLE系统的小型机的IDLE值偏低(甚至出现IDLE为0的情况,这时用户会惊呼数据库系统会瘫...
  • Oracle数据库业务优化心得 公司开发的产品基本上都使用ORACLE数据库,而且业务系统中存储和使用的数据量大,使用业务系统的用户也多。在系统忙时,大约会有一千个用户同事访问数据库系统,因此经常会有用户抱怨...
  • 连接oracle服务器超;有如下原因可能会影响。 网络不好;oracle服务器跟本地网络不好。 oracle服务器内存不足;导致反应超 监听日志listener.log太大;导致响应超。 所以对监听日志文件(listener.log)...
  • mysql与Oracle的区别

    万次阅读 多人点赞 2017-08-10 11:22:45
    mysql与Oracle的区别
  • oracle 数据库访问性能优化

    千次阅读 2016-02-21 18:17:38
    而大多数情况性能最的设备会是瓶颈点,如下载时网络速度可能会是瓶颈点,本地复制文件时硬盘可能会是瓶颈点,为什么这些一般的工作我们能快速确认瓶颈点呢,因为我们对这些慢速设备的性能数据有一些基本的认识,如...
  • oracle碎片

    千次阅读 2011-06-28 10:34:00
    oracle更是如此,当随着数据增加,oracle处理海量数据本身就已经费力了啊,如果再有大量的碎片,那就是雪上加霜啊。所以碎片要引起dba的高度重视,尽早发现尽早处理。碎片是怎么产生的呢?简单理解就
  • SQL语句执行时,Oracle的优化器会根据统计信息确定表的访问方式,一般来说,有两种基本的数据访问方式:1)全扫描。在全扫描(全表扫描或者快速全索引扫描)中,多个块被读入到一个IO运算中。2)索引扫描。索引扫描...
  • Oracle语言

    千次阅读 2008-07-29 21:13:00
    一、Oracle语言 Oracle 数据库系统使用经验 1.having 子句的用法 having 子句对 group by 子句所确定的行组进行控制 ,having 子句条件中只允许涉及常量 , 聚组函数或 group by 子句中的列 . 2. 外部联接 "+" 的...
  • 2、 本文许多示例及概念是基于Oracle数据库描述,对于其它关系型数据库也可以参考,但许多观点不适合于KV数据库或内存数据库或者是基于SSD技术的数据库; 3、 本文未深入数据库优化中最核心的执行计划分析技术。 ...
  • 那么问题来了,我们总不可能直接对生产环境的数据进行操作然后分析吧(以免影响生产环境的业务),所以必须从生产环境中将大量的数据复制到本地oracle db,再做分析。本人对于这次的跨环境跨库数据复制有着深深的...
  • Oracle-锁解读

    千次阅读 2016-11-03 14:13:05
    概念数据库是一个多用户使用的共享资源。当多个用户并发地存取数据时,在数据库中就会产生多个事务同时存取同一数据的情况。若对并发操作不加控制就可能会...Oracle 利用其锁机制来实现事务间的数据并发访问及数据一
  • Oracle优化

    千次阅读 2009-12-05 15:33:00
    1. 访问Table的方式ORACLE 采用两种访问表中记录的方式:a. 全表扫描全表扫描就是顺序地访问表中每条记录. ORACLE采用一次读入多个数据块(database block)的方式优化全表扫描.b. 通过ROWID访问表你可以采用基于ROWID...
  • ORACLEsql

    千次阅读 2013-11-19 21:26:12
    自学ORACLE的笔记,希望有所帮助
  • MySQL和Oracle的区别

    万次阅读 多人点赞 2019-07-14 10:31:15
    2、Oracle支持大并发,大访问量,是OLTP的最好的工具。 3、安装占用的内存也是有差别,Mysql安装完成之后占用的内存远远小于Oracle所占用的内存,并且Oracle越用所占内存也会变多。 二、微观上: 1、对于事务的支持 ...
  • Oracle笔记

    千次阅读 2011-06-30 22:33:00
    Oracle SQL day1 Oracle SQL(Oracle 9i 9.2.0.1.0) 一、DataBase 保存数据,以表的形式表现数据二、SQL SQL(structurequery language 结构化查询语言),是操作关系型数据库中的对象
  • Oracle Spatial

    千次阅读 2011-11-09 15:24:23
    Oracle Spatial主要通过元数据表、空间数据字段(即sdo_Geometry字段)和空间索引来管理空间数据,并在此基础上提供一系列空间查询和空间分析的程序包,让用户进行更深层次的GIS应用开发。Oracle Spatial使用空间...
  • Oracle 笔记

    千次阅读 2009-12-29 23:47:00
    Oracle 的使用 1.1. SQLPLUS 的命令 初始化表的位置: setNLS_LANG=american_america.us7ascii (设置编码才可以使用下面脚本) cd$ORACLE_HOME/rdbms cd demo summit2.sql ***********************
  • <Oracle优化新常态> 前半生

    千次阅读 2017-08-24 15:21:39
    ORACLE 优化 新常态
  • Oracle SQL性能优化

    千次阅读 2012-06-15 16:45:05
    ORACLE的解析器按照从右到左的顺序处理FROM子句中的表名,FROM子句中写在最后的表(基础表 driving table)将被最先处理,在FROM子句中包含多个表的情况下,你必须选择记录条数最少的表作为基础表。如果有3个以上的表...
  • 韩顺平Oracle笔记

    万次阅读 2011-09-07 10:24:00
    韩顺平玩转Oracle9i 1. Oracle认证和安装,与其他数据库比较 Oracle安装会自动的生成sys用户和system用户: (1)sys用户是超级用户,具有最高权限,具有sysdba角色,有create database的权限,该用户默认的...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 29,148
精华内容 11,659
关键字:

业务访问oracle很慢