วิธีการส่งคืนเฉพาะวันที่จากประเภทข้อมูล DateTime ของ SQL Server


1778
SELECT GETDATE()

ผลตอบแทน: 2008-09-22 15:24:13.790

ฉันต้องการส่วนวันที่โดยไม่มีส่วนเวลา: 2008-09-22 00:00:00.000

ฉันจะรับสิ่งนั้นได้อย่างไร


4
หากคุณกำลังมองหาประเภทข้อมูลวันที่โดยไม่มีเวลาแม้ว่าเวลาจะเป็น 00:00:00 คุณก็จะโชคไม่ดีคุณสามารถรับ varchar ได้ แต่โครงสร้างนั้นเป็นช่วงเวลาและคุณจะมีเวลาพอสมควร
Quintin Robinson

16
สิ่งหนึ่งที่ควรทราบคือ SQL Server 2008 มีประเภทข้อมูล DATE ที่แยกต่างหากสำหรับการจัดเก็บเพียงแค่วันที่โดยไม่มีองค์ประกอบเวลา ข้อมูลเพิ่มเติมที่นี่: sql-server-performance.com/articles/dev/datetime_2008_p1.aspx
Ben Hoffstein

7
อย่าพลาดโพสต์นี้ที่แสดงผลการทดสอบประสิทธิภาพของวิธีการกำจัดเวลาต่างๆ
ErikE

18
อย่าเข้าใจผิดด้วยคะแนนโหวตและคำตอบที่ยอมรับลองดูที่stackoverflow.com/a/126984/1155650
Rohit Vipin Mathews

8
@ โรฮิทคุณเข้าใจผิดว่าปี 2008 เป็นเวอร์ชั่นเดียวที่คนสนใจ (มีอีกหลายรุ่นในป่า) การโหวตจะพูดเพื่อตัวเอง
hktegner

คำตอบ:


2487

ในSQL Server 2008และสูงกว่าคุณควรCONVERTถึงวันที่:

SELECT CONVERT(date, getdate())

ในเวอร์ชันที่เก่ากว่าคุณสามารถทำสิ่งต่อไปนี้:

SELECT DATEADD(dd, 0, DATEDIFF(dd, 0, @your_date))

ตัวอย่างเช่น

SELECT DATEADD(dd, 0, DATEDIFF(dd, 0, GETDATE()))

ให้ฉัน

2008-09-22 00:00:00.000

ข้อดี:

  • ไม่จำเป็นต้องมีการแปลงvarchar<->datetime
  • ไม่จำเป็นต้องคิดเกี่ยวกับ locale

ตามที่ไมเคิลแนะนำ

ใช้ตัวแปรนี้: SELECT DATEADD(dd, DATEDIFF(dd, 0, getdate()), 0)

select getdate()

SELECT DATEADD(hh, DATEDIFF(hh, 0, getdate()), 0)
SELECT DATEADD(hh, 0, DATEDIFF(hh, 0, getdate()))

SELECT DATEADD(dd, DATEDIFF(dd, 0, getdate()), 0)
SELECT DATEADD(dd, 0, DATEDIFF(dd, 0, getdate()))

SELECT DATEADD(mm, DATEDIFF(mm, 0, getdate()), 0)
SELECT DATEADD(mm, 0, DATEDIFF(mm, 0, getdate()))

SELECT DATEADD(yy, DATEDIFF(yy, 0, getdate()), 0)
SELECT DATEADD(yy, 0, DATEDIFF(yy, 0, getdate()))

เอาท์พุท:

2019-04-19 08:09:35.557

2019-04-19 08:00:00.000
4763-02-17 00:00:00.000

2019-04-19 00:00:00.000
2019-04-19 00:00:00.000

2019-04-01 00:00:00.000
1903-12-03 00:00:00.000

2019-01-01 00:00:00.000
1900-04-30 00:00:00.000

52
+1 ดูเหมือนว่าวิธีนี้จะเร็วกว่าวิธีแปลงคู่ () 35% ที่ใช้กันทั่วไป (ซึ่งฉันใช้มาหลายปีด้วย) ทำได้ดีนี่.
Dane

8
ข้อเสียเพียงอย่างเดียวที่ฉันเห็นได้จากวิธีแก้ปัญหาของคุณคือถ้าคุณไม่ทราบว่ามันกำลังทำอะไรอยู่ การใช้วิธีการแปลงสองครั้งจะทำให้ความตั้งใจของคุณชัดเจนขึ้นสำหรับผู้ดูแลรหัสล่วงหน้า BTW ฉันไม่ได้ลงคะแนนคุณ ฉันคิดว่าฉันจะเริ่มใช้วิธีการของคุณด้วย Thankyou @aku
Jim Birchall

38
@pilavdzice การตั้งค่าวันที่และเวลาจนถึงเที่ยงคืนของวันนั้นทำให้ไม่ต้องเสียเวลา คุณคาดหวังผลอะไร datetimeชนิดข้อมูลไม่สามารถมีเวลาที่ไม่ทั้งหมด ฉันคิดว่าคุณกำลังสับสนในการจัดเก็บข้อมูลด้วยการนำเสนอของผู้ใช้ หากสิ่งที่คุณต้องการคือวิธีที่จะแสดงให้ผู้ใช้เห็นสตริงที่ไม่มีส่วนเวลา (ไม่ใช่ศูนย์เพียงแค่ว่าง) จากนั้นคุณก็ต้องการConvert(varchar(30), @Date, 101)หรือสิ่งที่คล้ายกัน ดูSQL Server Books Online •แปลงและแปลงสำหรับข้อมูลเพิ่มเติม
ErikE

7
@ user1671639 ชนิดข้อมูลวันที่และเวลามีทั้งวันที่และเวลาคุณไม่สามารถจัดเก็บได้โดยไม่ต้องใช้ข้อมูลอื่น - ถ้าคุณใช้ SQL Server 2008 ในกรณีนี้จะมีข้อมูล 'วันที่' และ 'เวลา' แยกต่างหาก ประเภท หากคุณใช้ CONVERT () เช่นนั้นคุณต้องการสตริงเพื่อใช้ในภายหลังดังนั้นคุณจะติดอยู่กับที่ทำเช่นนั้น - แม้ว่าจะดีกว่าถ้าคุณใช้ฟังก์ชั่นการจัดรูปแบบวันที่แทนการตัดวันที่ออก - หรือผ่านCAST(... AS DATE)หรือCONVERT(DATE, ...)ซึ่งมีการกล่าวถึงค่อนข้างบ่อยในหน้านี้
Magnus

10
ฉันขอแนะนำให้เปลี่ยนคำตอบเป็นSELECT DATEADD(dd, DATEDIFF(dd, 0, @your_date), 0)เพราะddสามารถสลับdatepartคำหลักอื่นเพื่อตัดทอนของคุณdatetimeในระดับที่กำหนดเองได้
ไมเคิล - Clay Shirky อยู่ที่ไหน

717

SQLServer 2008 มีชนิดข้อมูล 'วันที่' ซึ่งมีเฉพาะวันที่ที่ไม่มีคอมโพเนนต์เวลา ทุกคนที่ใช้ SQLServer 2008 ขึ้นไปสามารถทำสิ่งต่อไปนี้ได้:

SELECT CONVERT(date, GETDATE())

41
นอกจากนี้ยังมีชนิดข้อมูล 'เวลา' ใน SQL2008 ซึ่งจะตอบคำถามอีกครึ่งหนึ่งของการแยกวันที่และเวลา
misteraidan

8
FYI ฉันเปรียบเทียบวิธีการตัดเวลาที่แตกต่างจากวันที่และนี่เป็นวิธีที่เร็วที่สุด ได้รับความแตกต่างมีขนาดเล็ก แต่เห็นได้ชัดว่าเร็วกว่าการประหารชีวิตจำนวนมาก
UnhandledExcepSean

2
wt เกี่ยวกับ sqlserver 2005 ??
ดร. MAF

@ Dr.MAF การทำให้วงกลมเสร็จสมบูรณ์คำตอบก่อนปี 2008 จะอยู่ที่นี่: stackoverflow.com/questions/113045/…
Frosty840

170

หากใช้ SQL 2008 ขึ้นไป:

select cast(getdate() as date)

3
@FredrickGauss: วันที่ประเภทใด คุณใช้ SQL Server เวอร์ชันใด
abatishchev

7
ระวัง! ประกาศ @ date1 datetime = '2015-09-30 20: 59: 59.999'; select cast (@ date1 as date) ส่งคืน '2015-10-01'
นิค

6
@Nick: นี่เป็นปัญหาของ DateTime ใช้DateTime2แทนและใช้งานได้ดี sqlfiddle.com/#!6/9eecb7/2833
abatishchev

8
@Nick เพื่อเติมเต็มการตอบสนองของ abatishchev @ date1 ของคุณนั้นเป็น2015-10-01เพราะDateTimeข้อ จำกัด โดยไม่ต้องพยายามใด ๆ ที่จะโยนDateมันอัตราผลตอบแทน2015-10-01มากเกินไป! declare @date1 datetime = '2015-09-30 23:59:59.999';select @date1=>2015-10-01
Frédéric

4
หนึ่งในเทคนิค SQL ที่จดจำได้ง่ายเหล่านี้ ขณะที่ไมค์กล่าวว่าเพียง 2008 เป็นต้นไป แต่ถ้าคุณพบว่ามีฐานข้อมูลอยู่ที่ไหนสักแห่งปี 2005 และก่อนหน้านี้คุณอาจจะมีปัญหามาก :)
NicVerAZ

73

DATEADD และ DATEDIFF ดีกว่าการแปลงเป็น varchar แบบสอบถามทั้งสองมีแผนการดำเนินการเหมือนกัน แต่แผนการดำเนินการส่วนใหญ่เกี่ยวกับกลยุทธ์การเข้าถึงข้อมูลและไม่เปิดเผยค่าใช้จ่ายโดยนัยที่เกี่ยวข้องกับเวลา CPU ที่ใช้เพื่อดำเนินการทุกส่วน หากมีการเรียกใช้แบบสอบถามทั้งสองเทียบกับตารางที่มีแถวนับล้านแถวเวลา CPU ที่ใช้ DateDiff จะใกล้เคียงกับ 1 / 3rd ของเวลาในการแปลง CPU!

หากต้องการดูแผนการดำเนินการสำหรับข้อความค้นหา:

set showplan_text on
GO 

ทั้ง DATEADD และ DATEDIFF จะดำเนินการ CONVERT_IMPLICIT

แม้ว่าโซลูชัน CONVERT นั้นจะง่ายกว่าและอ่านง่ายกว่าสำหรับบางโซลูชัน แต่จะช้ากว่า ไม่จำเป็นต้องแปลงกลับเป็น datetime (ซึ่งเซิร์ฟเวอร์กระทำโดยปริยาย) นอกจากนี้ยังไม่มีความต้องการที่แท้จริงในวิธีการ DateDiff สำหรับ DateAdd หลังจากนั้นเนื่องจากผลลัพธ์จำนวนเต็มจะถูกแปลงกลับไปเป็นวันที่และเวลาโดยนัย


เลือก CONVERT (varchar, MyDate, 101) จาก DatesTable

  |--Compute Scalar(DEFINE:([Expr1004]=CONVERT(varchar(30),[TEST].[dbo].[DatesTable].[MyDate],101)))
       |--Table Scan(OBJECT:([TEST].[dbo].[DatesTable]))

เลือก DATEADD (dd, 0, DATEDIFF (dd, 0, MyDate)) จาก DatesTable

  |--Compute Scalar(DEFINE:([Expr1004]=dateadd(day,(0),CONVERT_IMPLICIT(datetime,datediff(day,'1900-01-01 00:00:00.000',CONVERT_IMPLICIT(datetime,[TEST].[dbo].[DatesTable].[MyDate],0)),0))))
       |--Table Scan(OBJECT:([TEST].[dbo].[DatesTable]))

การใช้ FLOOR () ตามที่ @digi แนะนำให้มีประสิทธิภาพใกล้เคียงกับ DateDiff มากขึ้น แต่ไม่แนะนำให้ใช้เนื่องจากการคัดเลือกประเภทข้อมูล datetime เพื่อลอยและย้อนกลับไม่ได้ให้คุณค่าดั้งเดิมเสมอไป

จำเอาไว้ผู้ชาย: อย่าเชื่อใคร ดูสถิติประสิทธิภาพและทดสอบด้วยตัวเอง!

ระวังเมื่อคุณกำลังทดสอบผลลัพธ์ของคุณ การเลือกหลายแถวไปยังไคลเอนต์จะซ่อนความแตกต่างของประสิทธิภาพเนื่องจากจะใช้เวลานานกว่าในการส่งแถวผ่านเครือข่ายมากกว่าที่จะทำการคำนวณ ดังนั้นตรวจสอบให้แน่ใจว่าการทำงานสำหรับทุกแถวนั้นทำโดยเซิร์ฟเวอร์ แต่ไม่มีการส่ง rowset ไปยังไคลเอนต์

ดูเหมือนว่าจะมีความสับสนสำหรับบางคนเกี่ยวกับเมื่อการเพิ่มประสิทธิภาพแคชมีผลต่อการค้นหา การเรียกใช้แบบสอบถามสองชุดในชุดเดียวกันหรือในชุดงานแยกกันจะไม่มีผลกับการแคช ดังนั้นคุณสามารถหมดอายุแคชด้วยตนเองหรือเพียงแค่เรียกใช้แบบสอบถามไปมาหลายครั้ง การปรับให้เหมาะสมสำหรับเคียวรี # 2 จะมีผลกับเคียวรีใด ๆ ที่ตามมาดังนั้นโปรดดำเนินการ # 1 หากคุณต้องการ

นี่คือสคริปต์ทดสอบเต็มรูปแบบและผลการปฏิบัติงานที่พิสูจน์ว่า DateDiff เร็วกว่าการแปลงเป็น varchar อย่างมาก


Ricardo C การสอบสวนที่ดี! คุณใช้ SQL Server เวอร์ชันใด ในวิธี MSSQL2000 กับ dateiff นั้นเร็วขึ้นเล็กน้อยสำหรับฉัน
aku

เพื่อทราบฉันทำการทดสอบ 1,000,000 ครั้ง สำหรับความแตกต่างของประสิทธิภาพสถานการณ์ในโลกแห่งความเป็นจริงจะไม่สังเกตเห็นได้ชัดฉันเดา
aku

อ้าวฉันใช้ SQL Server 2005 Express สำหรับการทดสอบนี้ ฉันทำงานที่ปี 2000 ในที่ทำงานและฉันจะทดสอบกับตารางที่มีมากกว่า 24 ล้านแถวและดูว่ามีอะไรเกิดขึ้นบ้าง
Ricardo C

Aku ผลลัพธ์เดียวกัน ไม่มีความแตกต่างในประสิทธิภาพมากกว่าสิบล้านแถว
Ricardo C

5
การเรียกร้องเกี่ยวกับประสิทธิภาพที่เท่ากันนั้นไม่เป็นความจริง แน่นอนแผนการดำเนินการจะเหมือนเดิม !!! การวัดประสิทธิภาพในสิ่งเหล่านี้ต้องกระทำโดยการเปรียบเทียบการใช้งาน CPU ไม่ใช่การตรวจสอบแผนการดำเนินการ
ErikE

51

ลองสิ่งนี้:

SELECT CONVERT(VARCHAR(10),GETDATE(),111)

ข้อความข้างต้นแปลงรูปแบบปัจจุบันของคุณเป็นYYYY/MM/DDโปรดอ้างอิงลิงค์นี้เพื่อเลือกรูปแบบที่คุณต้องการ


5
สิ่งนี้จะส่งคืน '2008/09/22' สำหรับฉัน
eddiegroves

1
SELECT CONVERT (VARCHAR (10), GETDATE (), 101) เป็นmm/dd/yyyyรูปแบบ
หมัด

4
ถ้าคุณกำลังเรียงลำดับตามมูลค่าข้อความดิบ (นอก DB) แล้วรูปแบบ 'ญี่ปุ่น' จะดีกว่า
Simon_Weaver


21

สำหรับการกลับมาในรูปแบบวันที่

นักแสดง (วันที่สั่งซื้อ ณ วันที่)

รหัสข้างต้นจะทำงานใน sql server 2010

มันจะกลับมาเหมือน 12/12/2013

สำหรับ SQL Server 2012 ให้ใช้รหัสด้านล่าง

CONVERT(VARCHAR(10), OrderDate , 111)

1
สิ่งนี้ส่งคืนวันที่ฉันด้วยเวลาศูนย์ไม่ใช่แค่วันที่
โบฮีเมีย

1
ฉันจะรู้ได้ไหมว่าคุณใช้ SQL Server เวอร์ชั่นใด?
Mahesh ML

1
@MaheshML จะส่งคืนทั้งวันที่และเวลาใน MS SQL 2012
Marek

1
ทำงานได้อย่างมีเสน่ห์ใน SQL Azure
Martín Coll

5
@MaheshML ไม่มีสิ่งเช่น SQL Server 2010
SvenAelterman

21

คุณสามารถใช้CONVERTฟังก์ชั่นเพื่อคืนวันที่เท่านั้น ดูลิงค์ด้านล่าง:

การจัดการวันที่และเวลาใน SQL Server 2000

นักแสดงและการแปลง

ไวยากรณ์สำหรับการใช้งานฟังก์ชั่นการแปลงคือ:

CONVERT ( data_type [ ( length ) ] , expression [ , style ] ) 

16

หากคุณต้องการผลลัพธ์ที่เป็นvarcharคุณควรผ่านไป

SELECT CONVERT(DATE, GETDATE()) --2014-03-26
SELECT CONVERT(VARCHAR(10), GETDATE(), 111) --2014/03/26

ซึ่งได้กล่าวมาแล้วข้างต้น

หากคุณต้องการผลลัพธ์ในรูปแบบวันที่และเวลาคุณควรใช้แบบสอบถามใด ๆ ด้านล่าง

  1. SELECT CONVERT(DATETIME, CONVERT(VARCHAR(10), GETDATE(), 111)) AS OnlyDate 

    2014-03-26 00: 00: 00.000

  2. SELECT CONVERT(DATETIME, CONVERT(VARCHAR(10), GETDATE(), 112)) AS OnlyDate 

    2014-03-26 00: 00: 00.000

  3. DECLARE  @OnlyDate DATETIME
    SET @OnlyDate = DATEDIFF(DD, 0, GETDATE())
    SELECT @OnlyDate AS OnlyDate

    2014-03-26 00: 00: 00.000


14
SELECT CONVERT(VARCHAR,DATEADD(DAY,-1,GETDATE()),103) --21/09/2011

SELECT CONVERT(VARCHAR,DATEADD(DAY,-1,GETDATE()),101) --09/21/2011

SELECT CONVERT(VARCHAR,DATEADD(DAY,-1,GETDATE()),111) --2011/09/21

SELECT CONVERT(VARCHAR,DATEADD(DAY,-1,GETDATE()),107) --Sep 21, 2011

13

ใช้ FLOOR () - เพียงแค่ตัดเวลา

SELECT CAST(FLOOR(CAST(GETDATE() AS FLOAT)) AS DATETIME)

4
วิธีนี้ไม่ใช่วิธีที่เร็วที่สุดและยังสอนคนที่ชี้ให้เห็นว่าวันที่ลอยได้อย่างแม่นยำซึ่งไม่ใช่ โปรดดูโพสต์นี้เพื่อดูรายละเอียดเพิ่มเติม
ErikE

13

ถ้าคุณกำลังใช้SQL Server 2012 หรือรุ่นที่ดังกล่าวข้างต้น ,

ใช้Format()ฟังก์ชั่น

มีคำตอบและการจัดรูปแบบหลายประเภทสำหรับเซิร์ฟเวอร์ SQL อยู่แล้ว แต่วิธีการส่วนใหญ่ค่อนข้างคลุมเครือและเป็นเรื่องยากสำหรับคุณที่จะจำหมายเลขสำหรับประเภทรูปแบบหรือฟังก์ชั่นที่เกี่ยวข้องกับรูปแบบวันที่ที่ระบุ นั่นเป็นสาเหตุที่ทำให้เซิร์ฟเวอร์ SQL เวอร์ชันถัดไปมีตัวเลือกที่ดีกว่า

FORMAT ( value, format [, culture ] )

ตัวเลือกวัฒนธรรมมีประโยชน์อย่างมากเนื่องจากคุณสามารถระบุวันที่ตามผู้ชมของคุณ

คุณต้องจำไว้ d (สำหรับรูปแบบขนาดเล็ก) และ D (สำหรับรูปแบบยาว)

1. "d" - รูปแบบวันที่แบบสั้น

2009-06-15T13:45:30 -> 6/15/2009 (en-US)
2009-06-15T13:45:30 -> 15/06/2009 (fr-FR)
2009-06-15T13:45:30 -> 2009/06/15 (ja-JP)

2. "D" - รูปแบบวันที่แบบยาว

2009-06-15T13:45:30 -> Monday, June 15, 2009 (en-US)
2009-06-15T13:45:30 -> 15 июня 2009 г. (ru-RU)
2009-06-15T13:45:30 -> Montag, 15. Juni 2009 (de-DE)

ตัวอย่างเพิ่มเติมในแบบสอบถาม

DECLARE @d DATETIME = '10/01/2011';
SELECT FORMAT ( @d, 'd', 'en-US' ) AS 'US English Result'
      ,FORMAT ( @d, 'd', 'en-gb' ) AS 'Great Britain English Result'
      ,FORMAT ( @d, 'd', 'de-de' ) AS 'German Result'
      ,FORMAT ( @d, 'd', 'zh-cn' ) AS 'Simplified Chinese (PRC) Result'; 

SELECT FORMAT ( @d, 'D', 'en-US' ) AS 'US English Result'
      ,FORMAT ( @d, 'D', 'en-gb' ) AS 'Great Britain English Result'
      ,FORMAT ( @d, 'D', 'de-de' ) AS 'German Result'
      ,FORMAT ( @d, 'D', 'zh-cn' ) AS 'Chinese (Simplified PRC) Result';

US English Result Great Britain English Result  German Result Simplified Chinese (PRC) Result
----------------  ----------------------------- ------------- -------------------------------------
10/1/2011         01/10/2011                    01.10.2011    2011/10/1

US English Result            Great Britain English Result  German Result                    Chinese (Simplified PRC) Result
---------------------------- ----------------------------- -----------------------------  ---------------------------------------
Saturday, October 01, 2011   01 October 2011               Samstag, 1. Oktober 2011        2011101

หากคุณต้องการรูปแบบเพิ่มเติมคุณสามารถไปที่:

  1. สตริงรูปแบบวันที่และเวลามาตรฐาน
  2. สตริงรูปแบบวันที่และเวลาที่กำหนดเอง

12

หากคุณต้องการใช้ CONVERT และรับผลลัพธ์เช่นเดียวกับคำถามเดิมที่ตั้งไว้นั่นคือ yyyy-mm-dd จากนั้นใช้CONVERT(varchar(10),[SourceDate as dateTime],121)รหัสเดียวกันกับคำตอบของคู่ก่อนหน้านี้ แต่รหัสที่จะแปลงเป็น yyyy-mm-dd ที่มีเครื่องหมายขีดกลางคือ 121

ถ้าฉันสามารถใช้ Soapbox เป็นเวลาหนึ่งวินาทีการจัดรูปแบบนี้ไม่ได้อยู่ในระดับข้อมูลและนั่นเป็นสาเหตุที่เป็นไปไม่ได้หากไม่มี 'เคล็ดลับ' ค่าโสหุ้ยสูงจนไร้สาระจนถึง SQL Server 2008 เมื่อชนิดข้อมูลวันที่จริงเป็นจริง แนะนำ การแปลงข้อมูลดังกล่าวในระดับข้อมูลเป็นค่าใช้จ่ายจำนวนมากใน DBMS ของคุณ แต่ที่สำคัญกว่านั้นคือสิ่งที่สองที่คุณทำเช่นนี้คุณได้สร้างข้อมูลในหน่วยความจำกำพร้าที่ฉันคิดว่าคุณจะกลับไปสู่โปรแกรม คุณไม่สามารถนำมันกลับไปไว้ในคอลัมน์ 3NF + อื่น ๆ หรือเปรียบเทียบกับสิ่งที่พิมพ์โดยไม่ต้องเปลี่ยนกลับดังนั้นสิ่งที่คุณทำคือการแนะนำจุดที่ล้มเหลวและลบการอ้างอิงเชิงสัมพันธ์

คุณควรดำเนินการต่อและส่งคืนข้อมูล dateTime ของคุณไปยังโปรแกรมการโทรและในระดับชั้นนำเสนอทำการปรับเปลี่ยนสิ่งที่จำเป็น ทันทีที่คุณทำการแปลงสิ่งต่าง ๆ ก่อนส่งกลับไปยังผู้เรียกคุณกำลังลบความหวังทั้งหมดของการอ้างอิงที่สมบูรณ์จากแอปพลิเคชัน สิ่งนี้จะป้องกันการดำเนินการ UPDATE หรือ DELETE อีกครั้งเว้นแต่ว่าคุณทำการพลิกกลับแบบแมนนวลซึ่งจะเป็นการเปิดเผยข้อมูลของคุณถึงข้อผิดพลาดของมนุษย์ / รหัส / gremlin เมื่อไม่มีความจำเป็น


1
ยกเว้นพูดถ้าคุณต้องการแบบสอบถามที่ดึงระเบียนทั้งหมดที่ตรงกับวันที่ผู้ใช้ระบุเป็นส่วนวันที่ของเขตเวลาที่แน่นอน ขอให้โชคดีที่ทำเช่นนั้นเฉพาะในเลเยอร์การนำเสนอ (คุณไม่จำเป็นต้องแปลงคุณสามารถสามารถใช้คำนวณวัน แต่คุณได้รับความคิด ... )
แอนดรูลาซารัส

1
@ ถามว่าทำไมมันถึงสำคัญ คุณพูดว่าWHERE col >= @Date AND col < DATEADD(DAY, 1, @Date);- ไม่มีเหตุผลใดที่จะตัดเวลาออกจากคอลัมน์
Aaron Bertrand

1
@AaronBertrand ใช้งานได้โดยสมมติว่าอินพุต@Dateมีส่วนเวลาเป็นศูนย์เท่านั้น ในกรณีที่ไม่เป็นจริงคุณยังต้องรู้วิธีตัดเวลาฝั่งเซิร์ฟเวอร์ ฉันเห็นด้วยกับคำตอบนี้ว่าการจัดรูปแบบควรถูกปล่อยไว้ที่เลเยอร์การนำเสนอ แต่ฉันไม่เห็นด้วยกับความหมายว่าการออกจากส่วนหน้านั้นหมายความว่าคุณไม่จำเป็นต้องรู้วิธีตัดทอนอย่างรวดเร็ว
Andrew Lazarus

1
@Andrew สิ่งที่คุณต้องทำคือทำให้พารามิเตอร์อินพุต DATE ประเด็นของฉันยังคงอยู่ที่คุณไม่ควรใช้การตัดทอนใด ๆ กับคอลัมน์แม้ว่าจะเป็นสัญชาตญาณแรกของคนส่วนใหญ่
Aaron Bertrand

1
@AaronBertrand และที่ถือว่าคุณมีการควบคุมประเภทข้อมูลของพารามิเตอร์ ใช้ได้ในขั้นตอนการจัดเก็บไม่เป็นไปได้ในสถานการณ์อื่น ๆ ทำไมไม่ลองโยนเพื่อให้แน่ใจว่าพารามิเตอร์เป็นประเภทที่คุณต้องการและต้องการ?
Andrew Lazarus

10
SELECT DATEADD(DD, DATEDIFF(DD, 0, GETDATE()), 0)

SELECT DATEADD(DAY, 0, DATEDIFF(DAY,0, GETDATE()))

SELECT CONVERT(DATETIME, CONVERT(VARCHAR(10), GETDATE(), 101))

แก้ไข: สองวิธีแรกเป็นหลักเดียวกันและออกดำเนินการวิธีการแปลงเป็น varchar


1
วิธีการเหล่านี้ยอดเยี่ยม แต่คุณแนะนำให้ใช้วิธีใด?
eddiegroves

3
หมายเหตุว่า "ถูกต้อง" รุ่นของชั้นสองเป็นselect dateadd(dd, datediff(dd, 0, getdate()), 0)เพราะdds จากนั้นจะสามารถสลับออกใด ๆ ของคำหลักคลิปวันที่ที่ส่วนใด ๆ ที่คุณเลือก (โปรดทราบว่าเป็นเพียงตัวย่อ)datepartddday
Michael - Where's Clay Shirky

10

เพื่อให้ได้ผลลัพธ์ตามที่ระบุฉันใช้คำสั่งต่อไปนี้

SELECT CONVERT(DATETIME,CONVERT(DATE,GETDATE()))

ฉัน Holpe มันมีประโยชน์



7

หากคุณกำลังกำหนดผลลัพธ์ให้กับคอลัมน์หรือตัวแปรให้ระบุประเภท DATE และการแปลงจะเป็นนัย

DECLARE @Date DATE = GETDATE()   

SELECT @Date   --> 2017-05-03

6

ฉันคิดว่ามันจะใช้งานได้ในกรณีของคุณ:

CONVERT(VARCHAR(10),Person.DateOfBirth,111) AS BirthDate
//here date is obtained as 1990/09/25

6
DECLARE @yourdate DATETIME = '11/1/2014 12:25pm'    
SELECT CONVERT(DATE, @yourdate)

2
คำแนะนำนี้ได้รับการครอบคลุมโดยคำตอบอื่น ๆ (มากกว่าหนึ่งครั้ง)
Andriy M

6

โอเคแม้ว่าฉันจะสายไปหน่อย :) แต่นี่เป็นอีกวิธีหนึ่ง

SELECT CAST(FLOOR(CAST(GETDATE() AS FLOAT)) as DATETIME)

ผลลัพธ์

2008-09-22 00:00:00.000

และถ้าคุณใช้ SQL Server 2012 ขึ้นไปคุณสามารถใช้FORMAT()ฟังก์ชั่นเช่นนี้ได้ -

SELECT FORMAT(GETDATE(), 'yyyy-MM-dd')

ตัวอย่างแรกของคุณยังมีองค์ประกอบเวลา ประเด็นของคำถามคือจะลบออกได้อย่างไร
แซค

5

แม้จะใช้เซิร์ฟเวอร์ MSSQL โบราณ 7.0 แล้วโค้ดที่นี่ (ด้วยความอนุเคราะห์ของลิงค์นี้) ทำให้ฉันสามารถใช้รูปแบบวันที่ใดก็ได้ที่ฉันต้องการ

PRINT '1) Date/time in format MON DD YYYY HH:MI AM (OR PM): ' + CONVERT(CHAR(19),GETDATE())  
PRINT '2) Date/time in format MM-DD-YY: ' + CONVERT(CHAR(8),GETDATE(),10)  
PRINT '3) Date/time in format MM-DD-YYYY: ' + CONVERT(CHAR(10),GETDATE(),110) 
PRINT '4) Date/time in format DD MON YYYY: ' + CONVERT(CHAR(11),GETDATE(),106)
PRINT '5) Date/time in format DD MON YY: ' + CONVERT(CHAR(9),GETDATE(),6) 
PRINT '6) Date/time in format DD MON YYYY HH:MM:SS:MMM(24H): ' + CONVERT(CHAR(24),GETDATE(),113)

มันผลิตผลลัพธ์นี้:

1) Date/time in format MON DD YYYY HH:MI AM (OR PM): Feb 27 2015  1:14PM
2) Date/time in format MM-DD-YY: 02-27-15
3) Date/time in format MM-DD-YYYY: 02-27-2015
4) Date/time in format DD MON YYYY: 27 Feb 2015
5) Date/time in format DD MON YY: 27 Feb 15
6) Date/time in format DD MON YYYY HH:MM:SS:MMM(24H): 27 Feb 2015 13:14:46:630

5

วันที่:

เลือกการแปลง (วันที่ GETDATE ())
เลือกนักแสดง (GETDATE () ตามวันที่)

เวลา:

เลือกการแปลง (เวลา GETDATE (), 114)
เลือกนักแสดง (GETDATE () ตามเวลา)

5

เพียงคุณสามารถทำสิ่งนี้:

SELECT CONVERT(date, getdate())
SELECT DATEADD(dd, 0, DATEDIFF(dd, 0, @your_date))
SELECT DATEADD(dd, 0, DATEDIFF(dd, 0, GETDATE()))

เอาท์พุทเป็น:

2008-09-22 00:00:00.000

หรือเพียงทำเช่นนี้

SELECT CONVERT (DATE, GETDATE()) 'Date Part Only'

ผลลัพธ์:

Date Part Only
--------------
2013-07-14

4

ทำไมคุณไม่ใช้ DATE_FORMAT (your_datetiem_column, '% d-% m-% Y')

EX: select DATE_FORMAT( some_datetime_column, '%d-%m-%Y' ) from table_name

คุณสามารถเปลี่ยนลำดับของ m, d และปีโดยจัดเรียง'%d-%m-%Y'ส่วนใหม่


4

ฉันรู้ว่ามันเก่า แต่ฉันไม่เห็นว่ามีใครระบุด้วยวิธีนี้ จากสิ่งที่ฉันสามารถบอกได้นี่คือมาตรฐาน ANSI

SELECT CAST(CURRENT_TIMESTAMP AS DATE)

มันจะดีถ้า Microsoft สามารถรองรับตัวแปร CURRENT_DATE มาตรฐาน ANSI


select {fn current_date()} as todayทำงานได้สำหรับฉัน
ไบรอัน

@brianary - ดี แต่ไม่ใช่ ANSI SQL
สว่าง

นั่นยุติธรรมเพียงพอและคำตอบของคุณสามารถพกพาได้อย่างดี แต่ฉันคิดว่าตราบใดที่เราทำงานกับ T-SQL สิ่งนี้ก็ใช้ได้ (และแสดงให้เห็นว่าการใช้ ANSI CURRENT_DATE นั้นไม่สำคัญสำหรับ MS)
ไบรอันรี่

4

ฉันชอบสิ่งต่อไปนี้ที่ไม่ได้กล่าวถึง:

DATEFROMPARTS(DATEPART(yyyy, @mydatetime), DATEPART(mm, @mydatetime), DATEPART(dd, @mydatetime))

นอกจากนี้ยังไม่สนใจเกี่ยวกับท้องถิ่นหรือแปลงคู่ - แม้ว่า 'datepart' แต่ละอันอาจทำคณิตศาสตร์ได้ ดังนั้นอาจช้ากว่าวิธีลงวันที่เล็กน้อย แต่สำหรับฉันมันชัดเจนกว่ามาก โดยเฉพาะอย่างยิ่งเมื่อฉันต้องการจัดกลุ่มตามปีและเดือน (ตั้งค่าวันที่ 1)


4

เริ่มจาก SQL SERVER 2012 คุณสามารถทำสิ่งนี้:

SELECT FORMAT(GETDATE(), 'yyyy-MM-dd 00:00:00.000')



4

ในกรณีนี้วันที่เท่านั้นคุณจะต้องเรียกใช้แบบสอบถามนี้:

เลือกการแปลง (VARCHAR (10), getdate (), 111);ป้อนคำอธิบายรูปภาพที่นี่


นี่ควรเป็นคำตอบที่ยอมรับได้
noobprogrammer

3

คุณสามารถใช้ส่วนต่อไปนี้เพื่อจัดรูปแบบวันที่และจัดรูปแบบวันที่:

DATENAME => ส่งคืนสตริงอักขระที่แทนส่วนวันที่ที่ระบุของวันที่ที่ระบุ

DATEADD => DATEPART()ฟังก์ชั่นนี้ใช้เพื่อคืนส่วนหนึ่งของวันที่ / เวลาเช่นปี, เดือน, วัน, ชั่วโมง, นาที, ฯลฯ

DATEPART => ส่งคืนจำนวนเต็มที่แทนวันที่ที่ระบุของวันที่ที่ระบุ

CONVERT()=> CONVERT()ฟังก์ชั่นเป็นฟังก์ชั่นทั่วไปที่แปลงการแสดงออกของชนิดข้อมูลหนึ่งไปยังอีกประเภทหนึ่ง CONVERT()ฟังก์ชั่นสามารถใช้ในการแสดงข้อมูลวันที่ / เวลาในรูปแบบที่แตกต่างกัน

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.