别让强制类型转换偷走性能

本次主题:强制类型转换性能的影响

SQL跟踪过程中发现一些表结构的DEFAULT值和SQL语句存在字段类型不一致的现象。

虽然业务逻辑没有出错,但却造成了索引失效或者增加了优化的复杂度。其中表结构DEFAULT值不正确影响更加重大,因为他影响了很多关联的SQL语句,

问题一:表结构DEFAULT值类型错误

尴尬:已有业务数据量很大,是转换表的DEFAULT值呢还是用转换类型的函数索引优化?

示例:同样是CHAR(1)类型,有的DEFAULT值是0,有的是'0'

create table STATUS_NOTE

(

 CONTAINER_ID                 NUMBER not null,

 ……

 IS_PRINT                             CHAR(1) default 0,

 CHECK_RESULT              CHAR(1) default '0',

 DELETED_FLAG                CHAR(1) default 0,

)

分析:此表在DELETED_FLAG上有索引列,但是ORACLE优化器中提示:The predicate TO_NUMBER("CS"."DELETED_FLAG")=0

used at line ID 6 of the execution plan contains an implicit data type conversion on indexed column "DELETED_FLAG"。

因为在索引列上存在强制类型转换,导致索引失效,某SQL语句在改表上的执行计划的COST达到2023,

而如果该字段类型正确,那么COST值至少将下降到613,如此轻而易举的能够提升几倍性能,何乐而不为。

问题二:SQL语句中字段类型错误

示例:DELETED_FLAG是CHAR类型,但SQL语句确和整型比较

select t.id,t.MSG_TYPE,t.CONTENT,t.MODI_DATE,t.DELETED_FLAG

   from SEND_CONTROL t

   Where (t.state='0' )--Or t.state='2')

   And FUNC_AVAILABLE_DATE(t.CREATE_DATE,t.TRY_TIMES)<=Sysdate  And t.DELETED_FLAG=0

分析:此表未创建索引,ORACLE优化器提醒Consider running the Access Advisor to improve the physical schema design or creating the recommended index.

SEND_CONTROL("STATE",TO_NUMBER("DELETED_FLAG"))

提示创建("STATE",TO_NUMBER("DELETED_FLAG")索引,显然,由于SQL语句中DELETED_FLAG=0导致了强制类型转换。

如果真如优化器所述创建函数索引,那么其他正确的SQL语句反而又成了强制类型转换,在此情况下需要扭转错误的SQL语句。

优化前语句COST:

SELECT STATEMENT, GOAL = ALL_ROWS    Cost=855     Cardinality=1   Bytes=134

TABLE ACCESS FULL   Object owner=SUZHOU   Object name=SZ_SEND_CONTROL                   Cost=855         Cardinality=1   Bytes=134

优化后语句COST:

SELECT STATEMENT, GOAL = ALL_ROWS   Cost=2 Cardinality=1         Bytes=134

TABLE ACCESS BY INDEX ROWID       Object owner=SUZHOU          Object name=SEND_CONTROL  Cost=2 Cardinality=1         Bytes=134

 INDEX RANGE SCAN                  Object owner=SUZHOU          Object name=TEST1                   Cost=1 Cardinality=1

该语句在优化前COST为855,而如果语句字段类型正确,索引生肖,那么COST将降低为2,提升数百倍的性能,何其快哉。

时间: 2025-01-09 15:04:51

别让强制类型转换偷走性能的相关文章

函数指针的强制类型转换实现代码_C 语言

废话不多少,直接上代码 复制代码 代码如下: /********************************************************************************* 程序名称:函数指针的强制类型转换 ** 程序描述:** 性能提升:** 程序版本:V1.0*******************************************************************************/#include <stdio.h>

实用技巧 Java类型转换与强制类型转换

技巧|转换 如果你以前有编程经验,那么你已经知道把一种类型的值赋给另外类型的一个变量是相当常见的.如果这2种类型是兼容的,那么Java 将自动地进行转换.例如,把int 类型的值赋给long 类型的变量,总是可行的.然而,不是所有的类型都是兼容的,因此,不是所有的类型转换都是可以隐式实现的.例如,没有将double 型转换为byte 型的定义.幸好,获得不兼容的类型之间的转换仍然是可能的.要达到这个目的,你必须使用一个强制类型转换,它能完成两个不兼容的类型之间的显式变换.让我们看看自动类型转换和

php foreach 参数强制类型转换的问题

所以,为了防止这样的信息出现,我使用foreach的时候,都会把参数进行强制类型转换,形势如下: foreach((array)$arr as $key => $value); 这样做一直相安无事,就在前几天,突然出现了问题.我强制类型转换以后不能正常的调用object的方法了. 复制代码 代码如下: <?php class service implements Iterator{ function __construct($service_define,$filter=null){ $thi

C#中的AS、IS运算符和强制类型转换简介

as和强制转换之间最大的区别就在于如何处理用户自定义的转换.操作符 as和 is 都只检查被转换对象的运行时类型,并不执行其他的操作.如果被转换对象的运行时类型既不是所转换的目标类型,也不是其派生类型,那么转型将告失败.但是强制转型则会使用转换操作符来执行转型操作,这包括任何内建的数值转换(如:long转int). 一般情况我们应该先考虑使用as进行类型转换,然后再考虑使用is,最后才考虑使用强制转换. 如果你使用as来转换数据,那么用is来做检测是不必要的.只用检测返回类型是否为null就行了

struct-c# 在一个实现了隐式转换的结构体进行强制类型转换时报错

问题描述 c# 在一个实现了隐式转换的结构体进行强制类型转换时报错 50C 如题,我有一个结构体,类似这样: public struct AInt{ private int _a; public int ToInt() { reurn _a; } public static implicit operator int(AInt value) { return value.ToInt(); } public static implicit operator AInt(int value) { _a

浅谈PHP强制类型转换,慎用!_php技巧

PHP是一门弱类型的语言.这是它的优势和特点,但是有的时候你又不得不对类型进行相应的转换. 这个时候问题就来了.因为很多情况下,你会发现转换类型之后得到的数据和预期的值相差老大一截. 这里我以强制转换为整形作为例子. 看下面的代码,可以说你绝对不可能说出正确的答案.echo (int) 123.999999999999999; echo (int)   -1.999999999999999;echo (int)   -1.9999999999999999; echo (int)   -0.999

《Java 7程序设计入门经典》一2.13 使用强制类型转换

2.13 使用强制类型转换 尽管自动类型转换很有用,但是由于它们只能用于兼容类型间扩大范围的转换,它们也不能满足所有的编程需要.对于其他情况,只能运用强制类型转换.强制类型转换(cast)是告诉编译器将一种类型转换为另一种类型.所以,它需要显式类型转换.强制类型转换具有以下一般形式: (target-type) expression 这里,target-type指定特定表达式转化到何种目标类型.例如,如果想把表达式x/y的类型转换为int类型,可以写成: 这里,尽管变量x和y都是double类型

string-这句话等号右面是强制类型转换吗?

问题描述 这句话等号右面是强制类型转换吗? Map map111 = (Map) send(map);这句话等号右面是强制类型转换吗? 解决方案 看你的send返回的是什么类型.java规定,从抽象往具体转换,需要强制转换操作,反之不需要. 举例: send返回"中国人"类型,你用"人"接收,不需要转换.你用"北京人"接收,需要转换.假设它们的继承关系是 人-中国人-北京人 解决方案二: 就是强制转换,,但是若返回的不是map,,就会抛异常 解决

C++开发必看 四种强制类型转换的总结

C风格的强制类型转换(Type Cast)很简单,不管什么类型的转换统统是:   TYPE b = (TYPE)a C++风格的类型转换提供了4种类型转换操作符来应对不同场合的应用.   const_cast,字面上理解就是去const属性. static_cast,命名上理解是静态类型转换.如int转换成char. dynamic_cast,命名上理解是动态类型转换.如子类和父类之间的多态类型转换. reinterpreter_cast,仅仅重新解释类型,但没有进行二进制的转换. 4种类型转换