รูปแบบ DateTime เป็นรูปแบบ SQL โดยใช้ C #


111

ฉันกำลังพยายามบันทึกรูปแบบวันที่และเวลาปัจจุบันจาก C # และแปลงเป็นรูปแบบวันที่ของเซิร์ฟเวอร์ SQL yyyy-MM-dd HH:mm:ssดังนั้นฉันจึงสามารถใช้สำหรับUPDATEแบบสอบถาม

นี่เป็นรหัสแรกของฉัน:

DateTime myDateTime = DateTime.Now;
string sqlFormattedDate = myDateTime.Date.ToString("yyyy-MM-dd HH:mm:ss");

ผลลัพธ์ในวันที่นั้นใช้ได้ แต่เวลาคือ "12:00:00" เสมอดังนั้นฉันจึงเปลี่ยนรหัสเป็นดังต่อไปนี้:

string sqlFormattedDate = myDateTime.Date.ToString("yyyy-MM-dd") + " " + 
myDateTime.TimeOfDay.ToString("HH:mm:ss");

มันทำให้ฉันมีข้อผิดพลาดในการคอมไพล์:

FormatException ไม่สามารถจัดการได้

และแนะนำว่าฉันต้องแยกวิเคราะห์ ดังนั้นฉันจึงลองทำสิ่งนี้กับรหัสของฉันตามการวิจัยของฉันที่นี่ใน StackOverflow:

string sqlFormattedDate = myDateTime.Date.ToString("yyyy-MM-dd") + " " + 
myDateTime.Parse.TimeOfDay.ToString("HH:mm:ss");

หรือ

string sqlFormattedDate = myDateTime.Date.ToString("yyyy-MM-dd") + " " + 
myDateTime.tryParse.TimeOfDay.ToString("HH:mm:ss");

แต่มันบอกฉันว่ามันเป็นวิธีการที่ไม่ถูกต้องสำหรับบริบทที่กำหนด ฉันพยายามค้นหาวิธีแก้ปัญหาของฉันและฉันติดอยู่สองชั่วโมงแล้ว ฉันยังใหม่อยู่ใน C # คุณช่วยฉันหน่อยได้ไหม


คุณดู DateTime.TryParseExact แล้วหรือยัง?
ทิม


3
ทำไมไม่ใช้พารามิเตอร์เพื่ออัพเดตDateTimeหรือคุณจัดเก็บเป็นสตริง? นอกจากนี้ToStringในวันที่Dateจะบ่งบอกว่าเวลาอยู่เสมอ12:00:00
V4Vendetta

3
คุณควรใช้การสืบค้นแบบพาราเมตริกกับพารามิเตอร์ประเภทDATETIMEจากนั้นคุณสามารถหลีกเลี่ยงการแปลงทั้งหมดนี้ไปมาและกลับจากการแสดงสตริง!
marc_s

5
อย่างที่คนอื่น ๆ บอกการใช้พารามิเตอร์และเก็บทุกอย่างไว้เป็นdatetimeจุดเริ่มต้นที่ดี ยิ่งไปกว่านั้นทำไมคุณถึงส่งเซิร์ฟเวอร์ในเวลาปัจจุบัน - มันมีGETDATE()ฟังก์ชั่นที่สามารถเรียกได้ทั้งหมดในฝั่งเซิร์ฟเวอร์
Damien_The_Unbeliever

คำตอบ:


220

ลองดูด้านล่างนี้

DateTime myDateTime = DateTime.Now;
string sqlFormattedDate = myDateTime.ToString("yyyy-MM-dd HH:mm:ss.fff");

ขอบคุณมากฉันพยายามสตริง sqlFormattedDate = myDateTime.DateTime ... ด้วยเหตุผลบางอย่างนี่คือสิ่งที่ฉันต้องการบรรลุ
Ace Caserya

การค้นหาของฉันใน stackoverflow ยังคงอ้างถึงการอ้างอิงที่ไม่ถูกต้องแม้ว่าคำถามจะได้รับคำตอบหลายครั้ง แต่มือใหม่อย่างฉันก็ไม่สามารถเชื่อมโยงได้ด้วยเหตุนี้ ขอโทษทุกคนฉันจะปิดคำถามทันทีที่ทำได้
Ace Caserya

1
ฉันคิดว่ารูปแบบ C # "เรียงลำดับได้" ก็เหมือนกัน ดังนั้นคุณสามารถทำ myDateTime.Time ToString ("s");
ProVega

@ProVega มันดูไม่เหมือนกัน (.oString ('s') มี T แทนช่องว่างระหว่างวันที่และเวลา) - แต่ฉันสามารถยืนยันได้ว่าเซิร์ฟเวอร์ SQL แยกวิเคราะห์เหมือนกันโดยมีหรือไม่มี T ( ฉันอยู่ในปี 2012) ฉันเริ่มใช้ 's' เป็นรูปแบบวันที่และเวลาในการบันทึกของฉันแล้วฉันจะไปกับสิ่งนั้นฉันคิดว่าขอบคุณ!
Ian Grainger

1
ใช่ในหน้าอย่างเป็นทางการCAST และ CONVERT (Transact-SQL)พวกเขาใช้ชื่อ "ODBC canonical" สำหรับแบบฟอร์มที่มีช่องว่างแยกyyyy-MM-ddจากช่วงเวลาของวันและชื่อ "ISO8601" สำหรับฟอร์มที่มีอักขระคั่น กT. แต่ใช่ทั้งสองรูปแบบจะแปลงโดยปริยาย (และถูกต้อง) เป็นdatetimeไฟล์.
Jeppe Stig Nielsen

46

การใช้รูปแบบวันที่และเวลามาตรฐาน "s" จะช่วยให้มั่นใจได้ถึงความเข้ากันได้ระหว่างประเทศ (MM / dd เทียบกับ dd / MM):

myDateTime.ToString("s");

=> 2013-12-31T00:00:00

ตัวเลือกที่สมบูรณ์: (รหัส: ผลลัพธ์ตัวอย่าง)

d: 6/15/2008 
D: Sunday, June 15, 2008 
f: Sunday, June 15, 2008 9:15 PM 
F: Sunday, June 15, 2008 9:15:07 PM 
g: 6/15/2008 9:15 PM 
G: 6/15/2008 9:15:07 PM 
m: June 15 
o: 2008-06-15T21:15:07.0000000 
R: Sun, 15 Jun 2008 21:15:07 GMT 
s: 2008-06-15T21:15:07 
t: 9:15 PM 
T: 9:15:07 PM 
u: 2008-06-15 21:15:07Z 
U: Monday, June 16, 2008 4:15:07 AM 
y: June, 2008 

'h:mm:ss.ff t': 9:15:07.00 P 
'd MMM yyyy': 15 Jun 2008 
'HH:mm:ss.f': 21:15:07.0 
'dd MMM HH:mm:ss': 15 Jun 21:15:07 
'\Mon\t\h\: M': Month: 6 
'HH:mm:ss.ffffzzz': 21:15:07.0000-07:00

รองรับใน. NET Framework: 4.6, 4.5, 4, 3.5, 3.0, 2.0, 1.1, 1.0
การอ้างอิง: DateTime.ToStringวิธีการ


2
นี่ยังไม่ละเอียดพอ (คิดถึงมิลลิวินาที) และจะทำให้คุณมีปัญหาในการค้นหาที่อาศัยการเรียงลำดับตามวันที่
reijerh

หากต้องการรับชั่วโมงและนาทีเช่นกันคุณสามารถใช้การแปลงนี้: string sqlFormattedDate = YourDate ToString ("yyyy-MM-ddTHH: mm: ss", System.Globalization.CultureInfo.InvariantCulture);
netfed

ใช้myDateTime.ToString("o");แทนได้โดยมีหน่วยเป็นมิลลิวินาทีและอธิบายตามตัวอักษรว่า "รูปแบบวันที่ / เวลาไปกลับ" ในเอกสาร "s"มีคำอธิบายว่าเป็น "รูปแบบวันที่ / เวลาที่เรียงลำดับได้" เท่านั้นดังนั้นฉันจึงไม่แนะนำให้ใช้สำหรับสิ่งนี้ ดู: docs.microsoft.com/en-us/dotnet/standard/base-types/…
Deantwo

9

คำตอบที่ถูกต้องได้รับ "ใช้พารามิเตอร์" แล้ว การจัดรูปแบบวันที่และส่งต่อเป็นสตริงไปยัง SQL-Server อาจทำให้เกิดข้อผิดพลาดได้เนื่องจากขึ้นอยู่กับการตั้งค่าว่าจะตีความวันที่ทางฝั่งเซิร์ฟเวอร์อย่างไร ในยุโรปเราเขียนว่า "1.12.2012" เพื่อระบุวันที่ 1 ธันวาคม 2012 ในขณะที่ในประเทศอื่น ๆ อาจถือว่าเป็นวันที่ 12 มกราคม

เมื่อออกคำสั่งโดยตรงใน SSMS ฉันใช้รูปแบบ yyyymmddที่ดูเหมือนจะค่อนข้างทั่วไป ฉันไม่พบปัญหาใด ๆ ในการติดตั้งต่างๆที่ฉันทำงานอยู่

มีอีกรูปแบบหนึ่งที่ไม่ค่อยได้ใช้ซึ่งค่อนข้างแปลก แต่ใช้ได้กับทุกเวอร์ชัน:

select { d '2013-10-01' }

จะส่งคืนวันแรกของเดือนตุลาคม 2013

select { ts '2013-10-01 13:45:01' }

จะกลับมาในวันที่ 1 ตุลาคมเวลา 13:45:01 น

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


3

รหัสแรกของคุณจะทำงานโดยการทำเช่นนี้

DateTime myDateTime = DateTime.Now;
string sqlFormattedDate = myDateTime.ToString("yyyy-MM-dd HH:mm:ss"); //Remove myDateTime.Date part 

3

ปัญหาของคุณอยู่ในคุณสมบัติ "วันที่" ที่ตัดทอนDateTimeให้เป็นวันที่เท่านั้น คุณสามารถใส่การแปลงได้ดังนี้:

DateTime myDateTime = DateTime.Now;
string sqlFormattedDate = myDateTime.ToString("yyyy-MM-dd HH:mm:ss"); // <- No Date.ToString()!

3

หากคุณต้องการจัดเก็บวันที่ปัจจุบันในตารางเพื่อให้คุณสามารถใช้ได้

GETDATE ();

หรือส่งผ่านฟังก์ชันนี้เป็นพารามิเตอร์

เช่น. 'อัปเดต tblname set curdate = GETDATE () โดยที่ colname = 123'


ทำงานได้ดียิ่งขึ้นเมื่อเป็นค่าเริ่มต้นบนตาราง SQL เว้นแต่คุณกำลังใช้กรอบงานที่ไม่อนุญาตให้ใช้ค่าเริ่มต้น
Deantwo

2

คำตอบที่ฉันกำลังมองหาคือ:

DateTime myDateTime = DateTime.Now;
string sqlFormattedDate = myDateTime.ToString("yyyy-MM-dd HH:mm:ss");

ฉันได้เรียนรู้ด้วยว่าคุณสามารถทำได้ด้วยวิธีนี้:

DateTime myDateTime = DateTime.Now;
string sqlFormattedDate = myDateTime.ToString(myCountryDateFormat);

โดยที่ myCountryDateFormat สามารถเปลี่ยนแปลงได้ตามความต้องการ

โปรดทราบว่าแท็ก "คำถามนี้อาจมีคำตอบอยู่แล้วที่นี่:" ยังไม่ได้ตอบคำถามจริงเพราะอย่างที่คุณเห็นใช้ ". วันที่" แทนที่จะละเว้น ค่อนข้างสับสนสำหรับโปรแกรมเมอร์มือใหม่ของ. NET



1

ปัญหาของคุณอยู่ในDateคุณสมบัติที่ตัดทอนDateTimeให้เป็นปัจจุบันเท่านั้น คุณสามารถใส่การแปลงได้ดังนี้:

DateTime myDateTime = DateTime.Now;

string sqlFormattedDate = myDateTime.ToString("yyyy-MM-dd HH:mm:ss");

ขอบคุณ. สิ่งที่ฉันกำลังมองหา;) แปลกใจที่ Microsoft ไม่ได้เพิ่มแฟล็กหรือคำสั่งเพื่อทำสิ่งนี้ให้สั้นลง
Zeek2

1

มาใช้คลาส SqlDateTime ที่สร้างขึ้น

new SqlDateTime(DateTime.Now).ToSqlString()

แต่ยังคงต้องตรวจสอบค่าว่าง สิ่งนี้จะทำให้เกิดข้อยกเว้นล้น

new SqlDateTime(DateTime.MinValue).ToSqlString()

SqlDateTime overflow. Must be between 1/1/1753 12:00:00 AM and 12/31/9999 11:59:59 PM.


0

ฉันคิดว่าปัญหาคือเครื่องหมายคำพูดเดี่ยวสองรายการหายไป

นี่คือ sql ที่ฉันใช้กับ MSSMS:

WHERE checktime >= '2019-01-24 15:01:36.000' AND checktime <= '2019-01-25 16:01:36.000'

อย่างที่คุณเห็นมีสองอัญประกาศดังนั้นรหัสของคุณต้องเป็น:

string sqlFormattedDate = "'" + myDateTime.Date.ToString("yyyy-MM-dd") + " " + myDateTime.TimeOfDay.ToString("HH:mm:ss") + "'";

ใช้เครื่องหมายคำพูดเดียวสำหรับทุกสตริงใน MSSQL หรือแม้แต่ใน MySQL ฉันหวังว่านี่จะช่วยได้.




-1

หากคุณต้องการอัปเดตตารางด้วย DateTime นั้นคุณสามารถใช้สตริง SQL ของคุณได้ดังตัวอย่างนี้:

int fieldId;
DateTime myDateTime = DateTime.Now
string sql = string.Format(@"UPDATE TableName SET DateFieldName='{0}' WHERE FieldID={1}", myDateTime.ToString("yyyy-MM-dd HH:mm:ss"), fieldId.ToString());

3
คำถามนี้ได้รับคำตอบและยอมรับแล้วด้วยวิธีการแก้ปัญหาที่หรูหรากว่า "และคุณกำลังขาดหายไปปิด
ม.ค.

-1

อีกวิธีหนึ่งในการส่ง DateTime จาก C # ไปยัง SQL Server โดยไม่คำนึงถึงการตั้งค่าภาษา SQL Server

สมมติว่าการตั้งค่าภูมิภาคของคุณแสดงวันที่เป็น dd.MM.yyyy (มาตรฐานเยอรมัน '104') แล้ว

DateTime myDateTime = DateTime.Now;
string sqlServerDate = "CONVERT(date,'"+myDateTime+"',104)"; 

ส่งผ่านตัวแปรวันที่และเวลา C # ไปยังตัวแปรชนิดวันที่ของเซิร์ฟเวอร์ SQL โดยพิจารณาการแมปตามกฎ "104" วันที่เซิร์ฟเวอร์ Sql ได้รับ yyyy-MM-dd

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

ดูเพิ่มเติมเกี่ยวกับกฎ: https://www.techonthenet.com/sql_server/functions/convert.php


สิ่งนี้จะเรียกToString()DateTime ซึ่งเป็นการตั้งค่าวัฒนธรรมเฉพาะ หากเครื่องที่ส่งคำสั่ง SQL นี้ใช้การตั้งค่าวัฒนธรรมอื่นที่ไม่ใช่เซิร์ฟเวอร์ SQL เซิร์ฟเวอร์ SQL อาจเข้าใจผิดว่าเป็นอย่างอื่น อย่าทำอย่างนี้! ดู: docs.microsoft.com/en-us/dotnet/api/…
Deantwo
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.