2013-07-23 33 views
2

BETWEEN文檔描述(http://dev.mysql.com/doc/refman/5.5/en/comparison-operators.html#operator_between)我注意到一個奇怪的表情,我不能完全明白:有日期或時間值,使用CAST之間使用時明確日期/日期時間投

爲了達到最佳效果( )將這些值顯式轉換爲所需的數據類型。示例:如果將DATETIME與兩個DATE值進行比較,請將DATE值轉換爲DATETIME值。如果在比較DATE時使用字符串常量(如「2001-1-1」),則將該字符串轉換爲DATE。

所以,我有以下問題:

  1. 誰能提供一個例子,當它真的有必要(與這種解釋),當cast會改變這一結果或性能大幅提升。假設我們使用mysql定義的日期文字數量(http://dev.mysql.com/doc/refman/5.5/en/date-and-time-literals.html)之一。爲了簡單起見,讓它成爲YYYY-MM-DD'2013-07-26')格式(與你喜歡的任何日期)

  2. 任何人都可以澄清什麼「最好的結果」是什麼意思?結果是預期的,或者不是 - 在這種情況下什麼是「最好的」?

PS:目標mysql版本是最新的5.5版本和更新版本。

PPS:爲了澄清:

  • 的問題假設我們使用的日期時間/日期兼容列,而不是VARCHAR處理等
  • 的問題是要擴大型,不是縮小

回答

-1

看看簡單的例子(MySQL的5.6):

drop table dattes; 
create table dattes(
    id int, 
    da_te date, 
    name varchar(200) 
); 

set @x = 0; 
insert into dattes 
select (@x:[email protected]+1), 
     '2013-5-1' + interval @x day, 
     t.column_name 
from information_schema.columns t 
; 

,這裏是一個查詢:

Set @start_date = cast('2013-5-2' as date); 
Set @start_datetime = cast('2013-5-2 15:00' as datetime); 
Set @end_date = cast('2013-5-10' as date); 

select (Select sum(id) from dattes 
      where da_te between @start_date and @end_date) da_test1, 

     (Select sum(id) from dattes 
      where da_te between @start_datetime and @end_date) da_test2, 

     (Select sum(id) from dattes 
      where da_te between cast(@start_datetime as date) 
       and @end_date) da_test3 
; 
+ ------------- + ------------- + ------------- + 
| da_test1  | da_test2  | da_test3  | 
+ ------------- + ------------- + ------------- + 
| 45   | 44   | 45   | 
+ ------------- + ------------- + ------------- + 

人們預計,在第二種情況將MySQL的隱含@start_datetime轉換爲日期(因爲在表中的列da_te是日期) - >然而MySQL卻反其道而行之,它拓寬其他參數日期時間。由於這個表中的一條記錄被跳過('2013-5-2 00:00'<'2013-5-2 15:00')。

這會影響當然的性能(可能不會顯着,但有點),因爲MySql必須從日期到日期時間轉換所有列值(或索引值,如果有的話)。

+1

「這會影響性能,當然,因爲MySql必須將所有列值(或索引值,如果有的話)從日期轉換爲日期時間」---這根本不正確。加上'cast(@start_datetime as date)'請閱讀問題的PPS部分:問題**不是**關於類型縮小。對不起,但沒有答案。 – zerkms

+1

「因爲這個表中的一條記錄被跳過了'('2013-5-2 00:00'<'2013-5-2 15:00')'。」 ---這是** EXPECTED **行爲,因爲'00:00 <15:00' – zerkms

+1

'cast('2013-5-2 15:00'as datetime)'或'cast('2013-5- 2'作爲日期)' - 這沒有多大意義。如果沒有'cast()',它將完全相同。 – zerkms