坑描述:
公司的訂單表數據量巨大(億級),在進行查詢的時候,發現一個慢查詢。
背景:
數據庫:oracle
表:T_order
索引字段:create_date (字段類型 date)
慢查詢sql:
select * from T_order where create_date >= #{parameterDate}
慢查詢的原因:
如果JAVA中的屬性為DATE,而數據庫中是DATE類型的話,mybatis會默認將JAVA中DATE屬性映射到數據庫的Timestamp類型。此時字段 create_date 為date類型,參數parameterDate為timestamp類型,兩者的類型不一致。oracle數據庫會date類型轉換為timestamp類型(精確度小的類型轉換為精確度大的類型),因此實際執行的sql語句為:select * from T_order where to_timestamp(create_date ) >= #{parameterDate} 導致左邊的列用到函數。即索引列上使用函數后會導致索引失效,這樣一來就全表掃描了訂單庫,造成慢sql。
解決方法:
原因以及知道了,解決起來就容易了。
修改后的sql為:
select * from T_order where create_date >= cast(#{parameterDate} as date)
注意的點:
1、索引的使用。
2、MyBatis的類型轉換。
3、oracle的類型轉換。
4、to_timestamp(將date類型轉換為Timestamp類型),cast(將某種數據類型的表達式顯式轉換為另一種數據類型,在此將Timestamp轉換為date類型)這兩個函數的使用。