Trong Ruby on Rails, sự khác biệt giữa DateTime, Dấu thời gian, Thời gian và Ngày là gì?


414

Theo kinh nghiệm của tôi, việc có được ngày / giờ đúng khi lập trình luôn đầy rẫy nguy hiểm và sự khác biệt.

Ruby và Rails luôn lảng tránh tôi về điều này, nếu chỉ do số lượng tùy chọn quá lớn; Tôi không bao giờ có bất kỳ ý tưởng mà tôi nên chọn.

Khi tôi đang sử dụng Rails và xem các kiểu dữ liệu ActiveRecord, tôi có thể tìm thấy những điều sau đây

: datetime ,: dấu thời gian ,: thời gian và: ngày

và không biết sự khác biệt là gì hoặc nơi gotchas ẩn nấp.

Có gì khác biệt? Bạn sử dụng chúng để làm gì?

(PS tôi đang sử dụng Rails3)

Câu trả lời:


572

Sự khác biệt giữa các định dạng ngày / giờ khác nhau trong ActiveRecord không liên quan nhiều đến Rails và mọi thứ liên quan đến bất kỳ cơ sở dữ liệu nào bạn đang sử dụng.

Sử dụng MySQL như một ví dụ (nếu không có lý do khác vì nó là phổ biến nhất), bạn có DATE, DATETIME, TIMETIMESTAMPcác kiểu dữ liệu cột; cũng giống như bạn có CHAR, VARCHAR, FLOATINTEGER.

Vì vậy, bạn hỏi, sự khác biệt là gì? Vâng, một số trong số họ là tự giải thích. DATEchỉ lưu trữ một ngày, TIMEchỉ lưu trữ một thời gian trong ngày, trong khi DATETIMElưu trữ cả hai.

Sự khác biệt giữa DATETIMETIMESTAMPtinh tế hơn một chút: DATETIMEđược định dạng là YYYY-MM-DD HH:MM:SS. Phạm vi hợp lệ đi từ năm 1000 đến năm 9999 (và mọi thứ ở giữa. Mặc dù TIMESTAMP trông tương tự khi bạn lấy nó từ cơ sở dữ liệu, nhưng nó thực sự chỉ là một mặt trước cho dấu thời gian unix . Phạm vi hợp lệ của nó đi từ 1970 đến 2038. Sự khác biệt ở đây, ngoài những khác nhau được xây dựng trong các chức năng trong cơ sở dữ liệu, là không gian lưu trữ. Bởi vì DATETIMEcác cửa hàng mỗi chữ số trong năm, ngày tháng, giờ, phút và giây, nó sử dụng lên tổng cộng 8 byte. Như TIMESTAMPchỉ lưu trữ số trong vài giây kể từ 1970-01-01, nó sử dụng 4 byte.

Bạn có thể đọc thêm về sự khác biệt giữa các định dạng thời gian trong MySQL tại đây .

Cuối cùng, nó thuộc về những gì bạn cần cột ngày / thời gian để làm. Bạn có cần lưu trữ ngày và thời gian trước năm 1970 hoặc sau năm 2038 không? Sử dụng DATETIME. Bạn có cần phải lo lắng về kích thước cơ sở dữ liệu và bạn đang ở trong bộ đếm thời gian đó? Sử dụng TIMESTAMP. Bạn chỉ cần lưu trữ một ngày? Sử dụng DATE. Bạn chỉ cần lưu trữ một thời gian? Sử dụng TIME.

Đã nói tất cả những điều này, Rails thực sự đưa ra một số quyết định cho bạn . Cả hai :timestamp:datetimesẽ mặc định DATETIME, trong khi :date:timetương ứng DATETIME, tương ứng.

Điều này có nghĩa là trong Rails, bạn chỉ phải quyết định xem bạn cần lưu trữ ngày, giờ hay cả hai.


7
Đối với bản ghi, tôi thích dấu thời gian tuyệt đối (unix) vì định dạng YYYY-MM-DD phụ thuộc vào múi giờ được sử dụng. Vì vậy, khách hàng cần biết múi giờ của máy chủ và cần thực hiện chuyển đổi. Dấu thời gian tuyệt đối từ giây 1970 đến năm 1970 không có vấn đề đó.
n13

32
@ n13 Điểm hay, nhưng không thực sự là vấn đề trong Rails, vì nó chuyển đổi thành UTC trước khi chèn datetimes vào cơ sở dữ liệu.
vonconrad

13
Đây là một trong những bài viết hữu ích nhất trong vũ trụ Rails. Điều này nên được thêm vào hướng dẫn đường ray ...
Andrew

4
TIMECột của MySQL không hoàn toàn là "thời gian trong ngày", vì nó chấp nhận số giờ> 24; nó cũng có thể được sử dụng như "thời gian trôi qua".
nickgrim

6
Đây có phải là giống nhau trong các dbs khác? ví dụ như postgres?
Andy Hayden

24
  1. : datetime (8 byte)

    • Cửa hàng Ngày và Giờ được định dạng YYYY-MM-DD HH: MM: SS
    • Hữu ích cho các cột như birthday_date
  2. : dấu thời gian (4 byte)

    • Số lượng cửa hàng của giây kể từ 1970-01-01
    • Hữu ích cho các cột như update_at, created_at
  3. : ngày (3 byte)
    • Ngày cửa hàng
  4. : thời gian (3 byte)
    • Thời gian lưu trữ

3
Điều này giống với phiên bản TL: DR của câu trả lời được chấp nhận ở trên
Chidozie Nnachor

0

Đây là một lời giải thích tuyệt vời và chính xác tôi tìm thấy.

TIMESTAMP được sử dụng để theo dõi các thay đổi của hồ sơ và cập nhật mỗi khi thay đổi hồ sơ. DATETIME được sử dụng để lưu trữ giá trị cụ thể và tĩnh không bị ảnh hưởng bởi bất kỳ thay đổi nào trong hồ sơ.

TIMESTAMP cũng bị ảnh hưởng bởi các cài đặt liên quan đến TIME ZONE khác nhau. Dữ liệu không đổi.

TIMESTAMP đã chuyển đổi nội bộ múi giờ hiện tại sang UTC để lưu trữ và trong quá trình truy xuất, chuyển đổi trở lại múi giờ hiện tại. Cơ sở dữ liệu không thể làm điều này.

TIMESTAMP là 4 byte và DATETIME là 8 byte.

Phạm vi được hỗ trợ của TIMESTAMP: '1970-01-01 00:00:01 UTC đến' 2038-01-19 03:14:07 range Phạm vi được hỗ trợ của UTC DATETIME: '1000-01-01 00:00:00 đến' 9999 -12-31 23:59:59

nguồn: https://www.dbrnd.com/2015/09/difference-between-datetime-and-timestamp-in-mysql/#:~:text=DATETIME%20vs%20TIMESTAMP%3A,DATETIME%20is%20constant .

Cũng thế...

bảng với các loại "ngày" cột khác nhau và các loại di chuyển đường ray tương ứng tùy thuộc vào cơ sở dữ liệu

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.