class Time
A Time
object represents a date and time:
Time.new(2000, 1, 1, 0, 0, 0) # => 2000-01-01 00:00:00 -0600
Although its value can be expressed as a single numeric (see Epoch Seconds below), it can be convenient to deal with the value by parts:
t = Time.new(-2000, 1, 1, 0, 0, 0.0) # => -2000-01-01 00:00:00 -0600 t.year # => -2000 t.month # => 1 t.mday # => 1 t.hour # => 0 t.min # => 0 t.sec # => 0 t.subsec # => 0 t = Time.new(2000, 12, 31, 23, 59, 59.5) # => 2000-12-31 23:59:59.5 -0600 t.year # => 2000 t.month # => 12 t.mday # => 31 t.hour # => 23 t.min # => 59 t.sec # => 59 t.subsec # => (1/2)
Epoch Seconds¶ ↑
Epoch seconds is the exact number of seconds (including fractional subseconds) since the Unix Epoch, January 1, 1970.
You can retrieve that value exactly using method Time.to_r
:
Time.at(0).to_r # => (0/1) Time.at(0.999999).to_r # => (9007190247541737/9007199254740992)
Other retrieval methods such as Time#to_i
and Time#to_f
may return a value that rounds or truncates subseconds.
Time Resolution¶ ↑
A Time
object derived from the system clock (for example, by method Time.now
) has the resolution supported by the system.
Time Internal Representation¶ ↑
Time
implementation uses a signed 63 bit integer, Integer(T_BIGNUM), or Rational
. It is a number of nanoseconds since the Epoch. The signed 63 bit integer can represent 1823-11-12 to 2116-02-20. When Integer
or Rational
is used (before 1823, after 2116, under nanosecond), Time
works slower than when the signed 63 bit integer is used.
Ruby uses the C function “localtime” and “gmtime” to map between the number and 6-tuple (year,month,day,hour,minute,second). “localtime” is used for local time and “gmtime” is used for UTC.
Integer(T_BIGNUM) and Rational
has no range limit, but the localtime and gmtime has range limits due to the C types “time_t” and “struct tm”. If that limit is exceeded, Ruby extrapolates the localtime function.
The Time
class always uses the Gregorian calendar. I.e. the proleptic Gregorian calendar is used. Other calendars, such as Julian calendar, are not supported.
“time_t” can represent 1901-12-14 to 2038-01-19 if it is 32 bit signed integer, -292277022657-01-27 to 292277026596-12-05 if it is 64 bit signed integer. However “localtime” on some platforms doesn’t supports negative time_t (before 1970).
“struct tm” has tm_year member to represent years. (tm_year = 0 means the year 1900.) It is defined as int in the C standard. tm_year can represent between -2147481748 to 2147485547 if int is 32 bit.
Ruby supports leap seconds as far as if the C function “localtime” and “gmtime” supports it. They use the tz database in most Unix systems. The tz database has timezones which supports leap seconds. For example, “Asia/Tokyo” doesn’t support leap seconds but “right/Asia/Tokyo” supports leap seconds. So, Ruby supports leap seconds if the TZ environment variable is set to “right/Asia/Tokyo” in most Unix systems.
Examples¶ ↑
All of these examples were done using the EST timezone which is GMT-5.
Creating a New Time
Instance¶ ↑
You can create a new instance of Time
with Time.new
. This will use the current system time. Time.now
is an alias for this. You can also pass parts of the time to Time.new
such as year, month, minute, etc. When you want to construct a time this way you must pass at least a year. If you pass the year with nothing else time will default to January 1 of that year at 00:00:00 with the current system timezone. Here are some examples:
Time.new(2002) #=> 2002-01-01 00:00:00 -0500 Time.new(2002, 10) #=> 2002-10-01 00:00:00 -0500 Time.new(2002, 10, 31) #=> 2002-10-31 00:00:00 -0500
You can pass a UTC offset:
Time.new(2002, 10, 31, 2, 2, 2, "+02:00") #=> 2002-10-31 02:02:02 +0200
zone = timezone("Europe/Athens") # Eastern European Time, UTC+2 Time.new(2002, 10, 31, 2, 2, 2, zone) #=> 2002-10-31 02:02:02 +0200
You can also use Time.local
and Time.utc
to infer local and UTC timezones instead of using the current system setting.
You can also create a new time using Time.at
which takes the number of seconds (with subsecond) since the Unix Epoch.
Time.at(628232400) #=> 1989-11-28 00:00:00 -0500
Working with an Instance of Time
¶ ↑
Once you have an instance of Time
there is a multitude of things you can do with it. Below are some examples. For all of the following examples, we will work on the assumption that you have done the following:
t = Time.new(1993, 02, 24, 12, 0, 0, "+09:00")
Was that a monday?
t.monday? #=> false
What year was that again?
t.year #=> 1993
Was it daylight savings at the time?
t.dst? #=> false
What’s the day a year later?
t + (60*60*24*365) #=> 1994-02-24 12:00:00 +0900
How many seconds was that since the Unix Epoch?
t.to_i #=> 730522800
You can also do standard functions like compare two times.
t1 = Time.new(2010) t2 = Time.new(2011) t1 == t2 #=> false t1 == t1 #=> true t1 < t2 #=> true t1 > t2 #=> false Time.new(2010,10,31).between?(t1, t2) #=> true
What’s Here¶ ↑
First, what’s elsewhere. Class Time
:
-
Inherits from class Object.
-
Includes module Comparable.
Here, class Time
provides methods that are useful for:
-
{Creating
Time
objects}[rdoc-ref:Time@Methods+for+Creating]. -
{Fetching
Time
values}[rdoc-ref:Time@Methods+for+Fetching]. -
{Querying a
Time
object}[rdoc-ref:Time@Methods+for+Querying]. -
{Comparing
Time
objects}[rdoc-ref:Time@Methods+for+Comparing]. -
{Converting a
Time
object}[rdoc-ref:Time@Methods+for+Converting]. -
{Rounding a
Time
}.
Methods for Creating¶ ↑
-
::new
: Returns a new time from specified arguments (year, month, etc.), including an optional timezone value. -
::local
(aliased as::mktime
): Same as::new
, except the timezone is the local timezone. -
::utc
(aliased as::gm
): Same as::new
, except the timezone is UTC. -
::at
: Returns a new time based on seconds since epoch. -
::now
: Returns a new time based on the current system time. -
+
(plus): Returns a new time increased by the given number of seconds. -
-
(minus): Returns a new time decreased by the given number of seconds.
Methods for Fetching¶ ↑
-
year
: Returns the year of the time. -
hour
: Returns the hours value for the time. -
min
: Returns the minutes value for the time. -
sec
: Returns the seconds value for the time. -
usec
(aliased astv_usec
): Returns the number of microseconds in the subseconds value of the time. -
nsec
(aliased astv_nsec
: Returns the number of nanoseconds in the subsecond part of the time. -
subsec
: Returns the subseconds value for the time. -
wday
: Returns the integer weekday value of the time (0 == Sunday). -
yday
: Returns the integer yearday value of the time (1 == January 1). -
hash
: Returns the integer hash value for the time. -
utc_offset
(aliased asgmt_offset
andgmtoff
): Returns the offset in seconds between time and UTC. -
to_f
: Returns the float number of seconds since epoch for the time. -
to_i
(aliased astv_sec
): Returns the integer number of seconds since epoch for the time. -
to_r
: Returns theRational
number of seconds since epoch for the time. -
zone
: Returns a string representation of the timezone of the time.
Methods for Querying¶ ↑
-
dst?
(aliased asisdst
): Returns whether the time is DST (daylight saving time). -
sunday?
: Returns whether the time is a Sunday. -
monday?
: Returns whether the time is a Monday. -
tuesday?
: Returns whether the time is a Tuesday. -
wednesday?
: Returns whether the time is a Wednesday. -
thursday?
: Returns whether the time is a Thursday. -
friday?
: Returns whether time is a Friday. -
saturday?
: Returns whether the time is a Saturday.
Methods for Comparing¶ ↑
Methods for Converting¶ ↑
-
inspect
: Returns the time in detail as a string. -
strftime
: Returns the time as a string, according to a given format. -
to_a
: Returns a 10-element array of values from the time. -
to_s
: Returns a string representation of the time. -
getutc
(aliased asgetgm
): Returns a new time converted to UTC. -
getlocal
: Returns a new time converted to local time. -
localtime
: Converts time to local time in place. -
deconstruct_keys
: Returns a hash of time components used in pattern-matching.
Methods for Rounding¶ ↑
-
round
:Returns a new time with subseconds rounded. -
ceil
: Returns a new time with subseconds raised to a ceiling. -
floor
: Returns a new time with subseconds lowered to a floor.
For the forms of argument zone
, see Timezone Specifiers.
Timezone Specifiers¶ ↑
Certain Time
methods accept arguments that specify timezones:
-
Time.at
: keyword argumentin:
. -
Time.new
: positional argumentzone
or keyword argumentin:
. -
Time.now
: keyword argumentin:
. -
Time#getlocal
: positional argumentzone
. -
Time#localtime
: positional argumentzone
.
The value given with any of these must be one of the following (each detailed below):
Hours/Minutes Offsets¶ ↑
The zone value may be a string offset from UTC in the form '+HH:MM'
or '-HH:MM'
, where:
-
HH
is the 2-digit hour in the range0..23
. -
MM
is the 2-digit minute in the range0..59
.
Examples:
t = Time.utc(2000, 1, 1, 20, 15, 1) # => 2000-01-01 20:15:01 UTC Time.at(t, in: '-23:59') # => 1999-12-31 20:16:01 -2359 Time.at(t, in: '+23:59') # => 2000-01-02 20:14:01 +2359
Single-Letter Offsets¶ ↑
The zone value may be a letter in the range 'A'..'I'
or 'K'..'Z'
; see List of military time zones:
t = Time.utc(2000, 1, 1, 20, 15, 1) # => 2000-01-01 20:15:01 UTC Time.at(t, in: 'A') # => 2000-01-01 21:15:01 +0100 Time.at(t, in: 'I') # => 2000-01-02 05:15:01 +0900 Time.at(t, in: 'K') # => 2000-01-02 06:15:01 +1000 Time.at(t, in: 'Y') # => 2000-01-01 08:15:01 -1200 Time.at(t, in: 'Z') # => 2000-01-01 20:15:01 UTC
Integer Offsets¶ ↑
The zone value may be an integer number of seconds in the range -86399..86399
:
t = Time.utc(2000, 1, 1, 20, 15, 1) # => 2000-01-01 20:15:01 UTC Time.at(t, in: -86399) # => 1999-12-31 20:15:02 -235959 Time.at(t, in: 86399) # => 2000-01-02 20:15:00 +235959
Timezone Objects¶ ↑
The zone value may be an object responding to certain timezone methods, an instance of Timezone and TZInfo for example.
The timezone methods are:
-
local_to_utc
:-
Called when
Time.new
is invoked withtz
as the value of positional argumentzone
or keyword argumentin:
. -
Argument: a Time-like object.
-
Returns: a Time-like object in the UTC timezone.
-
-
utc_to_local
:-
Called when
Time.at
orTime.now
is invoked withtz
as the value for keyword argumentin:
, and whenTime#getlocal
orTime#localtime
is called withtz
as the value for positional argumentzone
. -
Argument: a Time-like object.
-
Returns: a Time-like object in the local timezone.
-
A custom timezone class may have these instance methods, which will be called if defined:
-
abbr
:-
Called when
Time#strftime
is invoked with a format involving%Z
. -
Argument: a Time-like object.
-
Returns: a string abbreviation for the timezone name.
-
-
dst?
:-
Called when
Time.at
orTime.now
is invoked withtz
as the value for keyword argumentin:
, and whenTime#getlocal
orTime#localtime
is called withtz
as the value for positional argumentzone
. -
Argument: a Time-like object.
-
Returns: whether the time is daylight saving time.
-
-
name
:-
Called when
Marshal.dump(t)
is invoked -
Argument: none.
-
Returns: the string name of the timezone.
-
Time
-Like Objects¶ ↑
A Time
-like object is a container object capable of interfacing with timezone libraries for timezone conversion.
The argument to the timezone conversion methods above will have attributes similar to Time
, except that timezone related attributes are meaningless.
The objects returned by local_to_utc
and utc_to_local
methods of the timezone object may be of the same class as their arguments, of arbitrary object classes, or of class Integer
.
For a returned class other than Integer
, the class must have the following methods:
-
year
-
mon
-
mday
-
hour
-
min
-
sec
-
isdst
-
to_i
For a returned Integer
, its components, decomposed in UTC, are interpreted as times in the specified timezone.
Timezone Names¶ ↑
If the class (the receiver of class methods, or the class of the receiver of instance methods) has find_timezone
singleton method, this method is called to achieve the corresponding timezone object from a timezone name.
For example, using Timezone:
class TimeWithTimezone < Time require 'timezone' def self.find_timezone(z) = Timezone[z] end TimeWithTimezone.now(in: "America/New_York") #=> 2023-12-25 00:00:00 -0500 TimeWithTimezone.new("2023-12-25 America/New_York") #=> 2023-12-25 00:00:00 -0500
Or, using TZInfo:
class TimeWithTZInfo < Time require 'tzinfo' def self.find_timezone(z) = TZInfo::Timezone.get(z) end TimeWithTZInfo.now(in: "America/New_York") #=> 2023-12-25 00:00:00 -0500 TimeWithTZInfo.new("2023-12-25 America/New_York") #=> 2023-12-25 00:00:00 -0500
You can define this method per subclasses, or on the toplevel Time
class.
Constants
- VERSION
Public Class Methods
Returns a new Time
object based on the given arguments.
Required argument time
may be either of:
-
A
Time
object, whose value is the basis for the returned time; also influenced by optional keyword argumentin:
(see below). -
A numeric number of Epoch seconds for the returned time.
Examples:
t = Time.new(2000, 12, 31, 23, 59, 59) # => 2000-12-31 23:59:59 -0600 secs = t.to_i # => 978328799 Time.at(secs) # => 2000-12-31 23:59:59 -0600 Time.at(secs + 0.5) # => 2000-12-31 23:59:59.5 -0600 Time.at(1000000000) # => 2001-09-08 20:46:40 -0500 Time.at(0) # => 1969-12-31 18:00:00 -0600 Time.at(-1000000000) # => 1938-04-24 17:13:20 -0500
Optional numeric argument subsec
and optional symbol argument units
work together to specify subseconds for the returned time; argument units
specifies the units for subsec
:
-
:millisecond
:subsec
in milliseconds:Time.at(secs, 0, :millisecond) # => 2000-12-31 23:59:59 -0600 Time.at(secs, 500, :millisecond) # => 2000-12-31 23:59:59.5 -0600 Time.at(secs, 1000, :millisecond) # => 2001-01-01 00:00:00 -0600 Time.at(secs, -1000, :millisecond) # => 2000-12-31 23:59:58 -0600
-
:microsecond
or:usec
:subsec
in microseconds:Time.at(secs, 0, :microsecond) # => 2000-12-31 23:59:59 -0600 Time.at(secs, 500000, :microsecond) # => 2000-12-31 23:59:59.5 -0600 Time.at(secs, 1000000, :microsecond) # => 2001-01-01 00:00:00 -0600 Time.at(secs, -1000000, :microsecond) # => 2000-12-31 23:59:58 -0600
-
:nanosecond
or:nsec
:subsec
in nanoseconds:Time.at(secs, 0, :nanosecond) # => 2000-12-31 23:59:59 -0600 Time.at(secs, 500000000, :nanosecond) # => 2000-12-31 23:59:59.5 -0600 Time.at(secs, 1000000000, :nanosecond) # => 2001-01-01 00:00:00 -0600 Time.at(secs, -1000000000, :nanosecond) # => 2000-12-31 23:59:58 -0600
Optional keyword argument in: zone
specifies the timezone for the returned time:
Time.at(secs, in: '+12:00') # => 2001-01-01 17:59:59 +1200 Time.at(secs, in: '-12:00') # => 2000-12-31 17:59:59 -1200
For the forms of argument zone
, see Timezone Specifiers.
# File timev.rb, line 324 def self.at(time, subsec = false, unit = :microsecond, in: nil) if Primitive.mandatory_only? Primitive.time_s_at1(time) else Primitive.time_s_at(time, subsec, unit, Primitive.arg!(:in)) end end
Parses date
as an HTTP-date defined by RFC 2616 and converts it to a Time
object.
ArgumentError
is raised if date
is not compliant with RFC 2616 or if the Time
class cannot represent specified date.
See httpdate
for more information on this format.
require 'time' Time.httpdate("Thu, 06 Oct 2011 02:26:12 GMT") #=> 2011-10-06 02:26:12 UTC
You must require ‘time’ to use this method.
# File lib/time.rb, line 568 def httpdate(date) if date.match?(/\A\s* (?:Mon|Tue|Wed|Thu|Fri|Sat|Sun),\x20 (\d{2})\x20 (Jan|Feb|Mar|Apr|May|Jun|Jul|Aug|Sep|Oct|Nov|Dec)\x20 (\d{4})\x20 (\d{2}):(\d{2}):(\d{2})\x20 GMT \s*\z/ix) self.rfc2822(date).utc elsif /\A\s* (?:Monday|Tuesday|Wednesday|Thursday|Friday|Saturday|Sunday),\x20 (\d\d)-(Jan|Feb|Mar|Apr|May|Jun|Jul|Aug|Sep|Oct|Nov|Dec)-(\d\d)\x20 (\d\d):(\d\d):(\d\d)\x20 GMT \s*\z/ix =~ date year = $3.to_i if year < 50 year += 2000 else year += 1900 end self.utc(year, $2, $1.to_i, $4.to_i, $5.to_i, $6.to_i) elsif /\A\s* (?:Mon|Tue|Wed|Thu|Fri|Sat|Sun)\x20 (Jan|Feb|Mar|Apr|May|Jun|Jul|Aug|Sep|Oct|Nov|Dec)\x20 (\d\d|\x20\d)\x20 (\d\d):(\d\d):(\d\d)\x20 (\d{4}) \s*\z/ix =~ date self.utc($6.to_i, MonthValue[$1.upcase], $2.to_i, $3.to_i, $4.to_i, $5.to_i) else raise ArgumentError.new("not RFC 2616 compliant date: #{date.inspect}") end end
See as_json
.
# File ext/json/lib/json/add/time.rb, line 9 def self.json_create(object) if usec = object.delete('u') # used to be tv_usec -> tv_nsec object['n'] = usec * 1000 end if method_defined?(:tv_nsec) at(object['s'], Rational(object['n'], 1000)) else at(object['s'], object['n'] / 1000) end end
Like Time.utc
, except that the returned Time
object has the local timezone, not the UTC timezone:
# With seven arguments. Time.local(0, 1, 2, 3, 4, 5, 6) # => 0000-01-02 03:04:05.000006 -0600 # With exactly ten arguments. Time.local(0, 1, 2, 3, 4, 5, 6, 7, 8, 9) # => 0005-04-03 02:01:00 -0600
static VALUE time_s_mktime(int argc, VALUE *argv, VALUE klass) { struct vtm vtm; time_arg(argc, argv, &vtm); return time_localtime(time_new_timew(klass, timelocalw(&vtm))); }
Returns a new Time
object based on the given arguments, by default in the local timezone.
With no positional arguments, returns the value of Time.now
:
Time.new # => 2021-04-24 17:27:46.0512465 -0500
With one string argument that represents a time, returns a new Time
object based on the given argument, in the local timezone.
Time.new('2000-12-31 23:59:59.5') # => 2000-12-31 23:59:59.5 -0600 Time.new('2000-12-31 23:59:59.5 +0900') # => 2000-12-31 23:59:59.5 +0900 Time.new('2000-12-31 23:59:59.5', in: '+0900') # => 2000-12-31 23:59:59.5 +0900 Time.new('2000-12-31 23:59:59.5') # => 2000-12-31 23:59:59.5 -0600 Time.new('2000-12-31 23:59:59.56789', precision: 3) # => 2000-12-31 23:59:59.567 -0600
With one to six arguments, returns a new Time
object based on the given arguments, in the local timezone.
Time.new(2000, 1, 2, 3, 4, 5) # => 2000-01-02 03:04:05 -0600
For the positional arguments (other than zone
):
-
year
: Year, with no range limits:Time.new(999999999) # => 999999999-01-01 00:00:00 -0600 Time.new(-999999999) # => -999999999-01-01 00:00:00 -0600
-
month
: Month in range (1..12), or case-insensitive 3-letter month name:Time.new(2000, 1) # => 2000-01-01 00:00:00 -0600 Time.new(2000, 12) # => 2000-12-01 00:00:00 -0600 Time.new(2000, 'jan') # => 2000-01-01 00:00:00 -0600 Time.new(2000, 'JAN') # => 2000-01-01 00:00:00 -0600
-
mday
: Month day in range(1..31):Time.new(2000, 1, 1) # => 2000-01-01 00:00:00 -0600 Time.new(2000, 1, 31) # => 2000-01-31 00:00:00 -0600
-
hour
: Hour in range (0..23), or 24 ifmin
,sec
, andusec
are zero:Time.new(2000, 1, 1, 0) # => 2000-01-01 00:00:00 -0600 Time.new(2000, 1, 1, 23) # => 2000-01-01 23:00:00 -0600 Time.new(2000, 1, 1, 24) # => 2000-01-02 00:00:00 -0600
-
min
: Minute in range (0..59):Time.new(2000, 1, 1, 0, 0) # => 2000-01-01 00:00:00 -0600 Time.new(2000, 1, 1, 0, 59) # => 2000-01-01 00:59:00 -0600
-
sec
: Second in range (0…61):Time.new(2000, 1, 1, 0, 0, 0) # => 2000-01-01 00:00:00 -0600 Time.new(2000, 1, 1, 0, 0, 59) # => 2000-01-01 00:00:59 -0600 Time.new(2000, 1, 1, 0, 0, 60) # => 2000-01-01 00:01:00 -0600
Time.new(2000, 1, 1, 0, 0, 59.5) # => 2000-12-31 23:59:59.5 +0900 Time.new(2000, 1, 1, 0, 0, 59.7r) # => 2000-12-31 23:59:59.7 +0900
These values may be:
-
Integers, as above.
-
Numerics convertible to integers:
Time.new(Float(0.0), Rational(1, 1), 1.0, 0.0, 0.0, 0.0) # => 0000-01-01 00:00:00 -0600
-
String
integers:a = %w[0 1 1 0 0 0] # => ["0", "1", "1", "0", "0", "0"] Time.new(*a) # => 0000-01-01 00:00:00 -0600
When positional argument zone
or keyword argument in:
is given, the new Time
object is in the specified timezone. For the forms of argument zone
, see Timezone Specifiers:
Time.new(2000, 1, 1, 0, 0, 0, '+12:00') # => 2000-01-01 00:00:00 +1200 Time.new(2000, 1, 1, 0, 0, 0, in: '-12:00') # => 2000-01-01 00:00:00 -1200 Time.new(in: '-12:00') # => 2022-08-23 08:49:26.1941467 -1200
Since in:
keyword argument just provides the default, so if the first argument in single string form contains time zone information, this keyword argument will be silently ignored.
Time.new('2000-01-01 00:00:00 +0100', in: '-0500').utc_offset # => 3600
-
precision
: maximum effective digits in sub-second part, default is 9. More digits will be truncated, as other operations ofTime
. Ignored unless the first argument is a string.
# File timev.rb, line 435 def initialize(year = (now = true), mon = (str = year; nil), mday = nil, hour = nil, min = nil, sec = nil, zone = nil, in: nil, precision: 9) if zone if Primitive.arg!(:in) raise ArgumentError, "timezone argument given as positional and keyword arguments" end else zone = Primitive.arg!(:in) end if now return Primitive.time_init_now(zone) end if str and Primitive.time_init_parse(str, zone, precision) return self end Primitive.time_init_args(year, mon, mday, hour, min, sec, zone) end
Creates a new Time
object from the current system time. This is the same as Time.new
without arguments.
Time.now # => 2009-06-24 12:39:54 +0900 Time.now(in: '+04:00') # => 2009-06-24 07:39:54 +0400
For forms of argument zone
, see Timezone Specifiers.
# File timev.rb, line 265 def self.now(in: nil) Primitive.time_s_now(Primitive.arg!(:in)) end
Takes a string representation of a Time
and attempts to parse it using a heuristic.
This method **does not** function as a validator. If the input string does not match valid formats strictly, you may get a cryptic result. Should consider to use ‘Time.strptime` instead of this method as possible.
require 'time' Time.parse("2010-10-31") #=> 2010-10-31 00:00:00 -0500
Any missing pieces of the date are inferred based on the current date.
require 'time' # assuming the current date is "2011-10-31" Time.parse("12:00") #=> 2011-10-31 12:00:00 -0500
We can change the date used to infer our missing elements by passing a second object that responds to mon
, day
and year
, such as Date
, Time
or DateTime
. We can also use our own object.
require 'time' class MyDate attr_reader :mon, :day, :year def initialize(mon, day, year) @mon, @day, @year = mon, day, year end end d = Date.parse("2010-10-28") t = Time.parse("2010-10-29") dt = DateTime.parse("2010-10-30") md = MyDate.new(10,31,2010) Time.parse("12:00", d) #=> 2010-10-28 12:00:00 -0500 Time.parse("12:00", t) #=> 2010-10-29 12:00:00 -0500 Time.parse("12:00", dt) #=> 2010-10-30 12:00:00 -0500 Time.parse("12:00", md) #=> 2010-10-31 12:00:00 -0500
If a block is given, the year described in date
is converted by the block. This is specifically designed for handling two digit years. For example, if you wanted to treat all two digit years prior to 70 as the year 2000+ you could write this:
require 'time' Time.parse("01-10-31") {|year| year + (year < 70 ? 2000 : 1900)} #=> 2001-10-31 00:00:00 -0500 Time.parse("70-10-31") {|year| year + (year < 70 ? 2000 : 1900)} #=> 1970-10-31 00:00:00 -0500
If the upper components of the given time are broken or missing, they are supplied with those of now
. For the lower components, the minimum values (1 or 0) are assumed if broken or missing. For example:
require 'time' # Suppose it is "Thu Nov 29 14:33:20 2001" now and # your time zone is EST which is GMT-5. now = Time.parse("Thu Nov 29 14:33:20 2001") Time.parse("16:30", now) #=> 2001-11-29 16:30:00 -0500 Time.parse("7/23", now) #=> 2001-07-23 00:00:00 -0500 Time.parse("Aug 31", now) #=> 2001-08-31 00:00:00 -0500 Time.parse("Aug 2000", now) #=> 2000-08-01 00:00:00 -0500
Since there are numerous conflicts among locally defined time zone abbreviations all over the world, this method is not intended to understand all of them. For example, the abbreviation “CST” is used variously as:
-06:00 in America/Chicago, -05:00 in America/Havana, +08:00 in Asia/Harbin, +09:30 in Australia/Darwin, +10:30 in Australia/Adelaide, etc.
Based on this fact, this method only understands the time zone abbreviations described in RFC 822 and the system time zone, in the order named. (i.e. a definition in RFC 822 overrides the system time zone definition.) The system time zone is taken from Time.local(year, 1, 1).zone
and Time.local(year, 7, 1).zone
. If the extracted time zone abbreviation does not match any of them, it is ignored and the given time is regarded as a local time.
ArgumentError
is raised if Date._parse
cannot extract information from date
or if the Time
class cannot represent specified date.
This method can be used as a fail-safe for other parsing methods as:
Time.rfc2822(date) rescue Time.parse(date) Time.httpdate(date) rescue Time.parse(date) Time.xmlschema(date) rescue Time.parse(date)
A failure of Time.parse
should be checked, though.
You must require ‘time’ to use this method.
# File lib/time.rb, line 381 def parse(date, now=self.now) comp = !block_given? d = Date._parse(date, comp) year = d[:year] year = yield(year) if year && !comp make_time(date, year, d[:yday], d[:mon], d[:mday], d[:hour], d[:min], d[:sec], d[:sec_fraction], d[:zone], now) end
Parses date
as date-time defined by RFC 2822 and converts it to a Time
object. The format is identical to the date format defined by RFC 822 and updated by RFC 1123.
ArgumentError
is raised if date
is not compliant with RFC 2822 or if the Time
class cannot represent specified date.
See rfc2822
for more information on this format.
require 'time' Time.rfc2822("Wed, 05 Oct 2011 22:26:12 -0400") #=> 2010-10-05 22:26:12 -0400
You must require ‘time’ to use this method.
# File lib/time.rb, line 510 def rfc2822(date) if /\A\s* (?:(?:Mon|Tue|Wed|Thu|Fri|Sat|Sun)\s*,\s*)? (\d{1,2})\s+ (Jan|Feb|Mar|Apr|May|Jun|Jul|Aug|Sep|Oct|Nov|Dec)\s+ (\d{2,})\s+ (\d{2})\s* :\s*(\d{2}) (?:\s*:\s*(\d\d))?\s+ ([+-]\d{4}| UT|GMT|EST|EDT|CST|CDT|MST|MDT|PST|PDT|[A-IK-Z])/ix =~ date # Since RFC 2822 permit comments, the regexp has no right anchor. day = $1.to_i mon = MonthValue[$2.upcase] year = $3.to_i short_year_p = $3.length <= 3 hour = $4.to_i min = $5.to_i sec = $6 ? $6.to_i : 0 zone = $7 if short_year_p # following year completion is compliant with RFC 2822. year = if year < 50 2000 + year else 1900 + year end end off = zone_offset(zone) year, mon, day, hour, min, sec = apply_offset(year, mon, day, hour, min, sec, off) t = self.utc(year, mon, day, hour, min, sec) force_zone!(t, zone, off) t else raise ArgumentError.new("not RFC 2822 compliant date: #{date.inspect}") end end
Works similar to parse
except that instead of using a heuristic to detect the format of the input string, you provide a second argument that describes the format of the string.
Raises ‘ArgumentError` if the date or format is invalid.
If a block is given, the year described in date
is converted by the block. For example:
Time.strptime(...) {|y| y < 100 ? (y >= 69 ? y + 1900 : y + 2000) : y}
Below is a list of the formatting options:
- %a
-
The abbreviated weekday name (“Sun”)
- %A
-
The full weekday name (“Sunday”)
- %b
-
The abbreviated month name (“Jan”)
- %B
-
The full month name (“January”)
- %c
-
The preferred local date and time representation
- %C
-
Century (20 in 2009)
- %d
-
Day of the month (01..31)
- %D
-
Date
(%m/%d/%y) - %e
-
Day of the month, blank-padded ( 1..31)
- %F
-
Equivalent to %Y-%m-%d (the ISO 8601 date format)
- %g
-
The last two digits of the commercial year
- %G
-
The week-based year according to ISO-8601 (week 1 starts on Monday and includes January 4)
- %h
-
Equivalent to %b
- %H
-
Hour of the day, 24-hour clock (00..23)
- %I
-
Hour of the day, 12-hour clock (01..12)
- %j
-
Day of the year (001..366)
- %k
-
hour, 24-hour clock, blank-padded ( 0..23)
- %l
-
hour, 12-hour clock, blank-padded ( 0..12)
- %L
-
Millisecond of the second (000..999)
- %m
-
Month of the year (01..12)
- %M
-
Minute of the hour (00..59)
- %n
-
Newline (n)
- %N
-
Fractional seconds digits
- %p
-
Meridian indicator (“AM” or “PM”)
- %P
-
Meridian indicator (“am” or “pm”)
- %r
-
time, 12-hour (same as %I:%M:%S %p)
- %R
-
time, 24-hour (%H:%M)
- %s
-
Number of seconds since 1970-01-01 00:00:00 UTC.
- %S
-
Second of the minute (00..60)
- %t
-
Tab character (t)
- %T
-
time, 24-hour (%H:%M:%S)
- %u
-
Day of the week as a decimal, Monday being 1. (1..7)
- %U
-
Week number of the current year, starting with the first Sunday as the first day of the first week (00..53)
- %v
-
VMS date (%e-%b-%Y)
- %V
-
Week number of year according to ISO 8601 (01..53)
- %W
-
Week number of the current year, starting with the first Monday as the first day of the first week (00..53)
- %w
-
Day of the week (Sunday is 0, 0..6)
- %x
-
Preferred representation for the date alone, no time
- %X
-
Preferred representation for the time alone, no date
- %y
-
Year without a century (00..99)
- %Y
-
Year which may include century, if provided
- %z
-
Time
zone as hour offset from UTC (e.g. +0900) - %Z
-
Time
zone name - %%
-
Literal “%” character
- %+
-
date(1) (%a %b %e %H:%M:%S %Z %Y)
require 'time' Time.strptime("2000-10-31", "%Y-%m-%d") #=> 2000-10-31 00:00:00 -0500
You must require ‘time’ to use this method.
# File lib/time.rb, line 458 def strptime(date, format, now=self.now) d = Date._strptime(date, format) raise ArgumentError, "invalid date or strptime format - '#{date}' '#{format}'" unless d if seconds = d[:seconds] if sec_fraction = d[:sec_fraction] usec = sec_fraction * 1000000 usec *= -1 if seconds < 0 else usec = 0 end t = Time.at(seconds, usec) if zone = d[:zone] force_zone!(t, zone) end else year = d[:year] year = yield(year) if year && block_given? yday = d[:yday] if (d[:cwyear] && !year) || ((d[:cwday] || d[:cweek]) && !(d[:mon] && d[:mday])) # make_time doesn't deal with cwyear/cwday/cweek return Date.strptime(date, format).to_time end if (d[:wnum0] || d[:wnum1]) && !yday && !(d[:mon] && d[:mday]) yday = Date.strptime(date, format).yday end t = make_time(date, year, yday, d[:mon], d[:mday], d[:hour], d[:min], d[:sec], d[:sec_fraction], d[:zone], now) end t end
Returns a new Time
object based the on given arguments, in the UTC timezone.
With one to seven arguments given, the arguments are interpreted as in the first calling sequence above:
Time.utc(year, month = 1, mday = 1, hour = 0, min = 0, sec = 0, usec = 0)
Examples:
Time.utc(2000) # => 2000-01-01 00:00:00 UTC Time.utc(-2000) # => -2000-01-01 00:00:00 UTC
There are no minimum and maximum values for the required argument year
.
For the optional arguments:
-
month
: Month in range (1..12), or case-insensitive 3-letter month name:Time.utc(2000, 1) # => 2000-01-01 00:00:00 UTC Time.utc(2000, 12) # => 2000-12-01 00:00:00 UTC Time.utc(2000, 'jan') # => 2000-01-01 00:00:00 UTC Time.utc(2000, 'JAN') # => 2000-01-01 00:00:00 UTC
-
mday
: Month day in range(1..31):Time.utc(2000, 1, 1) # => 2000-01-01 00:00:00 UTC Time.utc(2000, 1, 31) # => 2000-01-31 00:00:00 UTC
-
hour
: Hour in range (0..23), or 24 ifmin
,sec
, andusec
are zero:Time.utc(2000, 1, 1, 0) # => 2000-01-01 00:00:00 UTC Time.utc(2000, 1, 1, 23) # => 2000-01-01 23:00:00 UTC Time.utc(2000, 1, 1, 24) # => 2000-01-02 00:00:00 UTC
-
min
: Minute in range (0..59):Time.utc(2000, 1, 1, 0, 0) # => 2000-01-01 00:00:00 UTC Time.utc(2000, 1, 1, 0, 59) # => 2000-01-01 00:59:00 UTC
-
sec
: Second in range (0..59), or 60 ifusec
is zero:Time.utc(2000, 1, 1, 0, 0, 0) # => 2000-01-01 00:00:00 UTC Time.utc(2000, 1, 1, 0, 0, 59) # => 2000-01-01 00:00:59 UTC Time.utc(2000, 1, 1, 0, 0, 60) # => 2000-01-01 00:01:00 UTC
-
usec
: Microsecond in range (0..999999):Time.utc(2000, 1, 1, 0, 0, 0, 0) # => 2000-01-01 00:00:00 UTC Time.utc(2000, 1, 1, 0, 0, 0, 999999) # => 2000-01-01 00:00:00.999999 UTC
The values may be:
-
Integers, as above.
-
Numerics convertible to integers:
Time.utc(Float(0.0), Rational(1, 1), 1.0, 0.0, 0.0, 0.0, 0.0) # => 0000-01-01 00:00:00 UTC
-
String
integers:a = %w[0 1 1 0 0 0 0 0] # => ["0", "1", "1", "0", "0", "0", "0", "0"] Time.utc(*a) # => 0000-01-01 00:00:00 UTC
When exactly ten arguments are given, the arguments are interpreted as in the second calling sequence above:
Time.utc(sec, min, hour, mday, month, year, dummy, dummy, dummy, dummy)
where the dummy
arguments are ignored:
a = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9] # => [0, 1, 2, 3, 4, 5, 6, 7, 8, 9] Time.utc(*a) # => 0005-04-03 02:01:00 UTC
This form is useful for creating a Time
object from a 10-element array returned by Time.to_a
:
t = Time.new(2000, 1, 2, 3, 4, 5, 6) # => 2000-01-02 03:04:05 +000006 a = t.to_a # => [5, 4, 3, 2, 1, 2000, 0, 2, false, nil] Time.utc(*a) # => 2000-01-02 03:04:05 UTC
The two forms have their first six arguments in common, though in different orders; the ranges of these common arguments are the same for both forms; see above.
Raises an exception if the number of arguments is eight, nine, or greater than ten.
Related: Time.local
.
static VALUE time_s_mkutc(int argc, VALUE *argv, VALUE klass) { struct vtm vtm; time_arg(argc, argv, &vtm); return time_gmtime(time_new_timew(klass, timegmw(&vtm))); }
Parses time
as a dateTime defined by the XML Schema and converts it to a Time
object. The format is a restricted version of the format defined by ISO 8601.
ArgumentError
is raised if time
is not compliant with the format or if the Time
class cannot represent the specified time.
See xmlschema
for more information on this format.
require 'time' Time.xmlschema("2011-10-05T22:26:12-04:00") #=> 2011-10-05 22:26:12-04:00
You must require ‘time’ to use this method.
# File lib/time.rb, line 622 def xmlschema(time) if /\A\s* (-?\d+)-(\d\d)-(\d\d) T (\d\d):(\d\d):(\d\d) (\.\d+)? (Z|[+-]\d\d(?::?\d\d)?)? \s*\z/ix =~ time year = $1.to_i mon = $2.to_i day = $3.to_i hour = $4.to_i min = $5.to_i sec = $6.to_i usec = 0 if $7 usec = Rational($7) * 1000000 end if $8 zone = $8 off = zone_offset(zone) year, mon, day, hour, min, sec = apply_offset(year, mon, day, hour, min, sec, off) t = self.utc(year, mon, day, hour, min, sec, usec) force_zone!(t, zone, off) t else self.local(year, mon, day, hour, min, sec, usec) end else raise ArgumentError.new("invalid xmlschema format: #{time.inspect}") end end
Return the number of seconds the specified time zone differs from UTC.
Numeric
time zones that include minutes, such as -10:00
or +1330
will work, as will simpler hour-only time zones like -10
or +13
.
Textual time zones listed in ZoneOffset are also supported.
If the time zone does not match any of the above, zone_offset
will check if the local time zone (both with and without potential Daylight Saving Time changes being in effect) matches zone
. Specifying a value for year
will change the year used to find the local time zone.
If zone_offset
is unable to determine the offset, nil will be returned.
require 'time' Time.zone_offset("EST") #=> -18000
You must require ‘time’ to use this method.
# File lib/time.rb, line 82 def zone_offset(zone, year=self.now.year) off = nil zone = zone.upcase if /\A([+-])(\d\d)(:?)(\d\d)(?:\3(\d\d))?\z/ =~ zone off = ($1 == '-' ? -1 : 1) * (($2.to_i * 60 + $4.to_i) * 60 + $5.to_i) elsif zone.match?(/\A[+-]\d\d\z/) off = zone.to_i * 3600 elsif ZoneOffset.include?(zone) off = ZoneOffset[zone] * 3600 elsif ((t = self.local(year, 1, 1)).zone.upcase == zone rescue false) off = t.utc_offset elsif ((t = self.local(year, 7, 1)).zone.upcase == zone rescue false) off = t.utc_offset end off end
Public Instance Methods
Returns a new Time
object whose value is the sum of the numeric value of self
and the given numeric
:
t = Time.new(2000) # => 2000-01-01 00:00:00 -0600 t + (60 * 60 * 24) # => 2000-01-02 00:00:00 -0600 t + 0.5 # => 2000-01-01 00:00:00.5 -0600
Related: Time#-
.
static VALUE time_plus(VALUE time1, VALUE time2) { struct time_object *tobj; GetTimeval(time1, tobj); if (IsTimeval(time2)) { rb_raise(rb_eTypeError, "time + time?"); } return time_add(tobj, time1, time2, 1); }
When numeric
is given, returns a new Time
object whose value is the difference of the numeric value of self
and numeric
:
t = Time.new(2000) # => 2000-01-01 00:00:00 -0600 t - (60 * 60 * 24) # => 1999-12-31 00:00:00 -0600 t - 0.5 # => 1999-12-31 23:59:59.5 -0600
When other_time
is given, returns a Float
whose value is the difference of the numeric values of self
and other_time
in seconds:
t - t # => 0.0
Related: Time#+
.
static VALUE time_minus(VALUE time1, VALUE time2) { struct time_object *tobj; GetTimeval(time1, tobj); if (IsTimeval(time2)) { struct time_object *tobj2; GetTimeval(time2, tobj2); return rb_Float(rb_time_unmagnify_to_float(wsub(tobj->timew, tobj2->timew))); } return time_add(tobj, time1, time2, -1); }
Compares self
with other_time
; returns:
-
-1
, ifself
is less thanother_time
. -
0
, ifself
is equal toother_time
. -
1
, ifself
is greater thenother_time
. -
nil
, ifself
andother_time
are incomparable.
Examples:
t = Time.now # => 2007-11-19 08:12:12 -0600 t2 = t + 2592000 # => 2007-12-19 08:12:12 -0600 t <=> t2 # => -1 t2 <=> t # => 1 t = Time.now # => 2007-11-19 08:13:38 -0600 t2 = t + 0.1 # => 2007-11-19 08:13:38 -0600 t.nsec # => 98222999 t2.nsec # => 198222999 t <=> t2 # => -1 t2 <=> t # => 1 t <=> t # => 0
static VALUE time_cmp(VALUE time1, VALUE time2) { struct time_object *tobj1, *tobj2; int n; GetTimeval(time1, tobj1); if (IsTimeval(time2)) { GetTimeval(time2, tobj2); n = wcmp(tobj1->timew, tobj2->timew); } else { return rb_invcmp(time1, time2); } if (n == 0) return INT2FIX(0); if (n > 0) return INT2FIX(1); return INT2FIX(-1); }
Methods Time#as_json
and Time.json_create
may be used to serialize and deserialize a Time object; see Marshal
.
Method Time#as_json
serializes self
, returning a 2-element hash representing self
:
require 'json/add/time' x = Time.now.as_json # => {"json_class"=>"Time", "s"=>1700931656, "n"=>472846644}
Method JSON.create
deserializes such a hash, returning a Time object:
Time.json_create(x) # => 2023-11-25 11:00:56.472846644 -0600
# File ext/json/lib/json/add/time.rb, line 36 def as_json(*) nanoseconds = [ tv_usec * 1000 ] respond_to?(:tv_nsec) and nanoseconds << tv_nsec nanoseconds = nanoseconds.max { JSON.create_id => self.class.name, 's' => tv_sec, 'n' => nanoseconds, } end
Returns a new Time
object whose numerical value is greater than or equal to self
with its seconds truncated to precision ndigits
:
t = Time.utc(2010, 3, 30, 5, 43, 25.123456789r) t # => 2010-03-30 05:43:25.123456789 UTC t.ceil # => 2010-03-30 05:43:26 UTC t.ceil(2) # => 2010-03-30 05:43:25.13 UTC t.ceil(4) # => 2010-03-30 05:43:25.1235 UTC t.ceil(6) # => 2010-03-30 05:43:25.123457 UTC t.ceil(8) # => 2010-03-30 05:43:25.12345679 UTC t.ceil(10) # => 2010-03-30 05:43:25.123456789 UTC t = Time.utc(1999, 12, 31, 23, 59, 59) t # => 1999-12-31 23:59:59 UTC (t + 0.4).ceil # => 2000-01-01 00:00:00 UTC (t + 0.9).ceil # => 2000-01-01 00:00:00 UTC (t + 1.4).ceil # => 2000-01-01 00:00:01 UTC (t + 1.9).ceil # => 2000-01-01 00:00:01 UTC
Related: Time#floor
, Time#round
.
static VALUE time_ceil(int argc, VALUE *argv, VALUE time) { VALUE ndigits, v, den; struct time_object *tobj; if (!rb_check_arity(argc, 0, 1) || NIL_P(ndigits = argv[0])) den = INT2FIX(1); else den = ndigits_denominator(ndigits); GetTimeval(time, tobj); v = w2v(rb_time_unmagnify(tobj->timew)); v = modv(v, den); if (!rb_equal(v, INT2FIX(0))) { v = subv(den, v); } return time_add(tobj, time, v, 1); }
Returns a string representation of self
, formatted by strftime('%a %b %e %T %Y')
or its shorthand version strftime('%c')
; see Formats for Dates and Times:
t = Time.new(2000, 12, 31, 23, 59, 59, 0.5) t.ctime # => "Sun Dec 31 23:59:59 2000" t.strftime('%a %b %e %T %Y') # => "Sun Dec 31 23:59:59 2000" t.strftime('%c') # => "Sun Dec 31 23:59:59 2000"
Related: Time#to_s
, Time#inspect
:
t.inspect # => "2000-12-31 23:59:59.5 +000001" t.to_s # => "2000-12-31 23:59:59 +0000"
static VALUE time_asctime(VALUE time) { return strftimev("%a %b %e %T %Y", time, rb_usascii_encoding()); }
Returns a hash of the name/value pairs, to use in pattern matching. Possible keys are: :year
, :month
, :day
, :yday
, :wday
, :hour
, :min
, :sec
, :subsec
, :dst
, :zone
.
Possible usages:
t = Time.utc(2022, 10, 5, 21, 25, 30) if t in wday: 3, day: ..7 # uses deconstruct_keys underneath puts "first Wednesday of the month" end #=> prints "first Wednesday of the month" case t in year: ...2022 puts "too old" in month: ..9 puts "quarter 1-3" in wday: 1..5, month: puts "working day in month #{month}" end #=> prints "working day in month 10"
Note that deconstruction by pattern can also be combined with class check:
if t in Time(wday: 3, day: ..7) puts "first Wednesday of the month" end
static VALUE time_deconstruct_keys(VALUE time, VALUE keys) { struct time_object *tobj; VALUE h; long i; GetTimeval(time, tobj); MAKE_TM_ENSURE(time, tobj, tobj->vtm.yday != 0); if (NIL_P(keys)) { h = rb_hash_new_with_size(11); rb_hash_aset(h, sym_year, tobj->vtm.year); rb_hash_aset(h, sym_month, INT2FIX(tobj->vtm.mon)); rb_hash_aset(h, sym_day, INT2FIX(tobj->vtm.mday)); rb_hash_aset(h, sym_yday, INT2FIX(tobj->vtm.yday)); rb_hash_aset(h, sym_wday, INT2FIX(tobj->vtm.wday)); rb_hash_aset(h, sym_hour, INT2FIX(tobj->vtm.hour)); rb_hash_aset(h, sym_min, INT2FIX(tobj->vtm.min)); rb_hash_aset(h, sym_sec, INT2FIX(tobj->vtm.sec)); rb_hash_aset(h, sym_subsec, quov(w2v(wmod(tobj->timew, WINT2FIXWV(TIME_SCALE))), INT2FIX(TIME_SCALE))); rb_hash_aset(h, sym_dst, RBOOL(tobj->vtm.isdst)); rb_hash_aset(h, sym_zone, time_zone(time)); return h; } if (UNLIKELY(!RB_TYPE_P(keys, T_ARRAY))) { rb_raise(rb_eTypeError, "wrong argument type %"PRIsVALUE" (expected Array or nil)", rb_obj_class(keys)); } h = rb_hash_new_with_size(RARRAY_LEN(keys)); for (i=0; i<RARRAY_LEN(keys); i++) { VALUE key = RARRAY_AREF(keys, i); if (sym_year == key) rb_hash_aset(h, key, tobj->vtm.year); if (sym_month == key) rb_hash_aset(h, key, INT2FIX(tobj->vtm.mon)); if (sym_day == key) rb_hash_aset(h, key, INT2FIX(tobj->vtm.mday)); if (sym_yday == key) rb_hash_aset(h, key, INT2FIX(tobj->vtm.yday)); if (sym_wday == key) rb_hash_aset(h, key, INT2FIX(tobj->vtm.wday)); if (sym_hour == key) rb_hash_aset(h, key, INT2FIX(tobj->vtm.hour)); if (sym_min == key) rb_hash_aset(h, key, INT2FIX(tobj->vtm.min)); if (sym_sec == key) rb_hash_aset(h, key, INT2FIX(tobj->vtm.sec)); if (sym_subsec == key) { rb_hash_aset(h, key, quov(w2v(wmod(tobj->timew, WINT2FIXWV(TIME_SCALE))), INT2FIX(TIME_SCALE))); } if (sym_dst == key) rb_hash_aset(h, key, RBOOL(tobj->vtm.isdst)); if (sym_zone == key) rb_hash_aset(h, key, time_zone(time)); } return h; }
Returns true
if self
is in daylight saving time, false
otherwise:
t = Time.local(2000, 1, 1) # => 2000-01-01 00:00:00 -0600 t.zone # => "Central Standard Time" t.dst? # => false t = Time.local(2000, 7, 1) # => 2000-07-01 00:00:00 -0500 t.zone # => "Central Daylight Time" t.dst? # => true
Returns true
if self
and other_time
are both Time
objects with the exact same time value.
static VALUE time_eql(VALUE time1, VALUE time2) { struct time_object *tobj1, *tobj2; GetTimeval(time1, tobj1); if (IsTimeval(time2)) { GetTimeval(time2, tobj2); return rb_equal(w2v(tobj1->timew), w2v(tobj2->timew)); } return Qfalse; }
Returns a new Time
object whose numerical value is less than or equal to self
with its seconds truncated to precision ndigits
:
t = Time.utc(2010, 3, 30, 5, 43, 25.123456789r) t # => 2010-03-30 05:43:25.123456789 UTC t.floor # => 2010-03-30 05:43:25 UTC t.floor(2) # => 2010-03-30 05:43:25.12 UTC t.floor(4) # => 2010-03-30 05:43:25.1234 UTC t.floor(6) # => 2010-03-30 05:43:25.123456 UTC t.floor(8) # => 2010-03-30 05:43:25.12345678 UTC t.floor(10) # => 2010-03-30 05:43:25.123456789 UTC t = Time.utc(1999, 12, 31, 23, 59, 59) t # => 1999-12-31 23:59:59 UTC (t + 0.4).floor # => 1999-12-31 23:59:59 UTC (t + 0.9).floor # => 1999-12-31 23:59:59 UTC (t + 1.4).floor # => 2000-01-01 00:00:00 UTC (t + 1.9).floor # => 2000-01-01 00:00:00 UTC
Related: Time#ceil
, Time#round
.
static VALUE time_floor(int argc, VALUE *argv, VALUE time) { VALUE ndigits, v, den; struct time_object *tobj; if (!rb_check_arity(argc, 0, 1) || NIL_P(ndigits = argv[0])) den = INT2FIX(1); else den = ndigits_denominator(ndigits); GetTimeval(time, tobj); v = w2v(rb_time_unmagnify(tobj->timew)); v = modv(v, den); return time_add(tobj, time, v, -1); }
Returns true
if self
represents a Friday, false
otherwise:
t = Time.utc(2000, 1, 7) # => 2000-01-07 00:00:00 UTC t.friday? # => true
Related: Time#saturday?
, Time#sunday?
, Time#monday?
.
static VALUE time_friday(VALUE time) { wday_p(5); }
Returns a new Time
object representing the value of self
converted to a given timezone; if zone
is nil
, the local timezone is used:
t = Time.utc(2000) # => 2000-01-01 00:00:00 UTC t.getlocal # => 1999-12-31 18:00:00 -0600 t.getlocal('+12:00') # => 2000-01-01 12:00:00 +1200
For forms of argument zone
, see Timezone Specifiers.
static VALUE time_getlocaltime(int argc, VALUE *argv, VALUE time) { VALUE off; if (rb_check_arity(argc, 0, 1) && !NIL_P(off = argv[0])) { VALUE zone = off; if (maybe_tzobj_p(zone)) { VALUE t = time_dup(time); if (zone_localtime(off, t)) return t; } if (NIL_P(off = utc_offset_arg(off))) { off = zone; if (NIL_P(zone = find_timezone(time, off))) invalid_utc_offset(off); time = time_dup(time); if (!zone_localtime(zone, time)) invalid_utc_offset(off); return time; } else if (off == UTC_ZONE) { return time_gmtime(time_dup(time)); } validate_utc_offset(off); time = time_dup(time); time_set_utc_offset(time, off); return time_fixoff(time); } return time_localtime(time_dup(time)); }
Returns a new Time
object representing the value of self
converted to the UTC timezone:
local = Time.local(2000) # => 2000-01-01 00:00:00 -0600 local.utc? # => false utc = local.getutc # => 2000-01-01 06:00:00 UTC utc.utc? # => true utc == local # => true
Returns the integer hash code for self
.
Related: Object#hash
.
static VALUE time_hash(VALUE time) { struct time_object *tobj; GetTimeval(time, tobj); return rb_hash(w2v(tobj->timew)); }
Returns the integer hour of the day for self
, in range (0..23):
t = Time.new(2000, 1, 2, 3, 4, 5, 6) # => 2000-01-02 03:04:05 +000006 t.hour # => 3
Related: Time#year
, Time#mon
, Time#min
.
static VALUE time_hour(VALUE time) { struct time_object *tobj; GetTimeval(time, tobj); MAKE_TM(time, tobj); return INT2FIX(tobj->vtm.hour); }
Returns a string which represents the time as RFC 1123 date of HTTP-date defined by RFC 2616:
day-of-week, DD month-name CCYY hh:mm:ss GMT
Note that the result is always UTC (GMT).
require 'time' t = Time.now t.httpdate # => "Thu, 06 Oct 2011 02:26:12 GMT"
You must require ‘time’ to use this method.
# File lib/time.rb, line 694 def httpdate getutc.strftime('%a, %d %b %Y %T GMT') end
Returns a string representation of self
with subseconds:
t = Time.new(2000, 12, 31, 23, 59, 59, 0.5) t.inspect # => "2000-12-31 23:59:59.5 +000001"
Related: Time#ctime
, Time#to_s
:
t.ctime # => "Sun Dec 31 23:59:59 2000" t.to_s # => "2000-12-31 23:59:59 +0000"
static VALUE time_inspect(VALUE time) { struct time_object *tobj; VALUE str, subsec; GetTimeval(time, tobj); str = strftimev("%Y-%m-%d %H:%M:%S", time, rb_usascii_encoding()); subsec = w2v(wmod(tobj->timew, WINT2FIXWV(TIME_SCALE))); if (subsec == INT2FIX(0)) { } else if (FIXNUM_P(subsec) && FIX2LONG(subsec) < TIME_SCALE) { long len; rb_str_catf(str, ".%09ld", FIX2LONG(subsec)); for (len=RSTRING_LEN(str); RSTRING_PTR(str)[len-1] == '0' && len > 0; len--) ; rb_str_resize(str, len); } else { rb_str_cat_cstr(str, " "); subsec = quov(subsec, INT2FIX(TIME_SCALE)); rb_str_concat(str, rb_obj_as_string(subsec)); } if (TZMODE_UTC_P(tobj)) { rb_str_cat_cstr(str, " UTC"); } else { /* ?TODO: subsecond offset */ long off = NUM2LONG(rb_funcall(tobj->vtm.utc_offset, rb_intern("round"), 0)); char sign = (off < 0) ? (off = -off, '-') : '+'; int sec = off % 60; int min = (off /= 60) % 60; off /= 60; rb_str_catf(str, " %c%.2d%.2d", sign, (int)off, min); if (sec) rb_str_catf(str, "%.2d", sec); } return str; }
Parses time
as a dateTime defined by the XML Schema and converts it to a Time
object. The format is a restricted version of the format defined by ISO 8601.
ArgumentError
is raised if time
is not compliant with the format or if the Time
class cannot represent the specified time.
See xmlschema
for more information on this format.
require 'time' Time.xmlschema("2011-10-05T22:26:12-04:00") #=> 2011-10-05 22:26:12-04:00
You must require ‘time’ to use this method.
With no argument given:
-
Returns
self
ifself
is a local time. -
Otherwise returns a new
Time
in the user’s local timezone:t = Time.utc(2000, 1, 1, 20, 15, 1) # => 2000-01-01 20:15:01 UTC t.localtime # => 2000-01-01 14:15:01 -0600
With argument zone
given, returns the new Time
object created by converting self
to the given time zone:
t = Time.utc(2000, 1, 1, 20, 15, 1) # => 2000-01-01 20:15:01 UTC t.localtime("-09:00") # => 2000-01-01 11:15:01 -0900
For forms of argument zone
, see Timezone Specifiers.
static VALUE time_localtime_m(int argc, VALUE *argv, VALUE time) { VALUE off; if (rb_check_arity(argc, 0, 1) && !NIL_P(off = argv[0])) { return time_zonelocal(time, off); } return time_localtime(time); }
Returns the integer minute of the hour for self
, in range (0..59):
t = Time.new(2000, 1, 2, 3, 4, 5, 6) # => 2000-01-02 03:04:05 +000006 t.min # => 4
Related: Time#year
, Time#mon
, Time#sec
.
static VALUE time_min(VALUE time) { struct time_object *tobj; GetTimeval(time, tobj); MAKE_TM(time, tobj); return INT2FIX(tobj->vtm.min); }
Returns the integer month of the year for self
, in range (1..12):
t = Time.new(2000, 1, 2, 3, 4, 5, 6) # => 2000-01-02 03:04:05 +000006 t.mon # => 1
Related: Time#year
, Time#hour
, Time#min
.
static VALUE time_mon(VALUE time) { struct time_object *tobj; GetTimeval(time, tobj); MAKE_TM(time, tobj); return INT2FIX(tobj->vtm.mon); }
Returns true
if self
represents a Monday, false
otherwise:
t = Time.utc(2000, 1, 3) # => 2000-01-03 00:00:00 UTC t.monday? # => true
Related: Time#tuesday?
, Time#wednesday?
, Time#thursday?
.
static VALUE time_monday(VALUE time) { wday_p(1); }
Returns the number of nanoseconds in the subseconds part of self
in the range (0..999_999_999); lower-order digits are truncated, not rounded:
t = Time.now # => 2022-07-11 15:04:53.3219637 -0500 t.nsec # => 321963700
Related: Time#subsec
(returns exact subseconds).
Returns a string which represents the time as date-time defined by RFC 2822:
day-of-week, DD month-name CCYY hh:mm:ss zone
where zone is [+-]hhmm.
If self
is a UTC time, -0000 is used as zone.
require 'time' t = Time.now t.rfc2822 # => "Wed, 05 Oct 2011 22:26:12 -0400"
You must require ‘time’ to use this method.
# File lib/time.rb, line 674 def rfc2822 strftime('%a, %d %b %Y %T ') << (utc? ? '-0000' : strftime('%z')) end
Returns a new Time
object whose numeric value is that of self
, with its seconds value rounded to precision ndigits
:
t = Time.utc(2010, 3, 30, 5, 43, 25.123456789r) t # => 2010-03-30 05:43:25.123456789 UTC t.round # => 2010-03-30 05:43:25 UTC t.round(0) # => 2010-03-30 05:43:25 UTC t.round(1) # => 2010-03-30 05:43:25.1 UTC t.round(2) # => 2010-03-30 05:43:25.12 UTC t.round(3) # => 2010-03-30 05:43:25.123 UTC t.round(4) # => 2010-03-30 05:43:25.1235 UTC t = Time.utc(1999, 12,31, 23, 59, 59) t # => 1999-12-31 23:59:59 UTC (t + 0.4).round # => 1999-12-31 23:59:59 UTC (t + 0.49).round # => 1999-12-31 23:59:59 UTC (t + 0.5).round # => 2000-01-01 00:00:00 UTC (t + 1.4).round # => 2000-01-01 00:00:00 UTC (t + 1.49).round # => 2000-01-01 00:00:00 UTC (t + 1.5).round # => 2000-01-01 00:00:01 UTC
Related: Time#ceil
, Time#floor
.
static VALUE time_round(int argc, VALUE *argv, VALUE time) { VALUE ndigits, v, den; struct time_object *tobj; if (!rb_check_arity(argc, 0, 1) || NIL_P(ndigits = argv[0])) den = INT2FIX(1); else den = ndigits_denominator(ndigits); GetTimeval(time, tobj); v = w2v(rb_time_unmagnify(tobj->timew)); v = modv(v, den); if (lt(v, quov(den, INT2FIX(2)))) return time_add(tobj, time, v, -1); else return time_add(tobj, time, subv(den, v), 1); }
Returns true
if self
represents a Saturday, false
otherwise:
t = Time.utc(2000, 1, 1) # => 2000-01-01 00:00:00 UTC t.saturday? # => true
Related: Time#sunday?
, Time#monday?
, Time#tuesday?
.
static VALUE time_saturday(VALUE time) { wday_p(6); }
Returns the integer second of the minute for self
, in range (0..60):
t = Time.new(2000, 1, 2, 3, 4, 5, 6) # => 2000-01-02 03:04:05 +000006 t.sec # => 5
Note: the second value may be 60 when there is a leap second.
Related: Time#year
, Time#mon
, Time#min
.
static VALUE time_sec(VALUE time) { struct time_object *tobj; GetTimeval(time, tobj); MAKE_TM(time, tobj); return INT2FIX(tobj->vtm.sec); }
Returns a string representation of self
, formatted according to the given string format
. See Formats for Dates and Times.
static VALUE time_strftime(VALUE time, VALUE format) { struct time_object *tobj; const char *fmt; long len; rb_encoding *enc; VALUE tmp; GetTimeval(time, tobj); MAKE_TM_ENSURE(time, tobj, tobj->vtm.yday != 0); StringValue(format); if (!rb_enc_str_asciicompat_p(format)) { rb_raise(rb_eArgError, "format should have ASCII compatible encoding"); } tmp = rb_str_tmp_frozen_acquire(format); fmt = RSTRING_PTR(tmp); len = RSTRING_LEN(tmp); enc = rb_enc_get(format); if (len == 0) { rb_warning("strftime called with empty format string"); return rb_enc_str_new(0, 0, enc); } else { VALUE str = rb_strftime_alloc(fmt, len, enc, time, &tobj->vtm, tobj->timew, TZMODE_UTC_P(tobj)); rb_str_tmp_frozen_release(format, tmp); if (!str) rb_raise(rb_eArgError, "invalid format: %"PRIsVALUE, format); return str; } }
Returns the exact subseconds for self
as a Numeric
(Integer
or Rational
):
t = Time.now # => 2022-07-11 15:11:36.8490302 -0500 t.subsec # => (4245151/5000000)
If the subseconds is zero, returns integer zero:
t = Time.new(2000, 1, 1, 2, 3, 4) # => 2000-01-01 02:03:04 -0600 t.subsec # => 0
static VALUE time_subsec(VALUE time) { struct time_object *tobj; GetTimeval(time, tobj); return quov(w2v(wmod(tobj->timew, WINT2FIXWV(TIME_SCALE))), INT2FIX(TIME_SCALE)); }
Returns true
if self
represents a Sunday, false
otherwise:
t = Time.utc(2000, 1, 2) # => 2000-01-02 00:00:00 UTC t.sunday? # => true
Related: Time#monday?
, Time#tuesday?
, Time#wednesday?
.
static VALUE time_sunday(VALUE time) { wday_p(0); }
Returns true
if self
represents a Thursday, false
otherwise:
t = Time.utc(2000, 1, 6) # => 2000-01-06 00:00:00 UTC t.thursday? # => true
Related: Time#friday?
, Time#saturday?
, Time#sunday?
.
static VALUE time_thursday(VALUE time) { wday_p(4); }
Returns a 10-element array of values representing self
:
Time.utc(2000, 1, 1).to_a # => [0, 0, 0, 1, 1, 2000, 6, 1, false, "UTC"] # [sec, min, hour, day, mon, year, wday, yday, dst?, zone]
The returned array is suitable for use as an argument to Time.utc
or Time.local
to create a new Time
object.
static VALUE time_to_a(VALUE time) { struct time_object *tobj; GetTimeval(time, tobj); MAKE_TM_ENSURE(time, tobj, tobj->vtm.yday != 0); return rb_ary_new3(10, INT2FIX(tobj->vtm.sec), INT2FIX(tobj->vtm.min), INT2FIX(tobj->vtm.hour), INT2FIX(tobj->vtm.mday), INT2FIX(tobj->vtm.mon), tobj->vtm.year, INT2FIX(tobj->vtm.wday), INT2FIX(tobj->vtm.yday), RBOOL(tobj->vtm.isdst), time_zone(time)); }
Returns a Date
object which denotes self.
static VALUE time_to_date(VALUE self) { VALUE y, nth, ret; int ry, m, d; y = f_year(self); m = FIX2INT(f_mon(self)); d = FIX2INT(f_mday(self)); decode_year(y, -1, &nth, &ry); ret = d_simple_new_internal(cDate, nth, 0, GREGORIAN, ry, m, d, HAVE_CIVIL); { get_d1(ret); set_sg(dat, DEFAULT_SG); } return ret; }
Returns a DateTime
object which denotes self.
static VALUE time_to_datetime(VALUE self) { VALUE y, sf, nth, ret; int ry, m, d, h, min, s, of; y = f_year(self); m = FIX2INT(f_mon(self)); d = FIX2INT(f_mday(self)); h = FIX2INT(f_hour(self)); min = FIX2INT(f_min(self)); s = FIX2INT(f_sec(self)); if (s == 60) s = 59; sf = sec_to_ns(f_subsec(self)); of = FIX2INT(f_utc_offset(self)); decode_year(y, -1, &nth, &ry); ret = d_complex_new_internal(cDateTime, nth, 0, 0, sf, of, GREGORIAN, ry, m, d, h, min, s, HAVE_CIVIL | HAVE_TIME); { get_d1(ret); set_sg(dat, DEFAULT_SG); } return ret; }
Returns the value of self
as a Float
number Epoch seconds; subseconds are included.
The stored value of self
is a Rational, which means that the returned value may be approximate:
Time.utc(1970, 1, 1, 0, 0, 0).to_f # => 0.0 Time.utc(1970, 1, 1, 0, 0, 0, 999999).to_f # => 0.999999 Time.utc(1950, 1, 1, 0, 0, 0).to_f # => -631152000.0 Time.utc(1990, 1, 1, 0, 0, 0).to_f # => 631152000.0
Related: Time#to_i
, Time#to_r
.
static VALUE time_to_f(VALUE time) { struct time_object *tobj; GetTimeval(time, tobj); return rb_Float(rb_time_unmagnify_to_float(tobj->timew)); }
Returns the value of self
as integer Epoch seconds; subseconds are truncated (not rounded):
Time.utc(1970, 1, 1, 0, 0, 0).to_i # => 0 Time.utc(1970, 1, 1, 0, 0, 0, 999999).to_i # => 0 Time.utc(1950, 1, 1, 0, 0, 0).to_i # => -631152000 Time.utc(1990, 1, 1, 0, 0, 0).to_i # => 631152000
static VALUE time_to_i(VALUE time) { struct time_object *tobj; GetTimeval(time, tobj); return w2v(wdiv(tobj->timew, WINT2FIXWV(TIME_SCALE))); }
Returns a JSON
string representing self
:
require 'json/add/time' puts Time.now.to_json
Output:
{"json_class":"Time","s":1700931678,"n":980650786}
# File ext/json/lib/json/add/time.rb, line 56 def to_json(*args) as_json.to_json(*args) end
Returns the value of self
as a Rational
exact number of Epoch seconds;
Time.now.to_r # => (16571402750320203/10000000)
Related: Time#to_f
, Time#to_i
.
static VALUE time_to_r(VALUE time) { struct time_object *tobj; VALUE v; GetTimeval(time, tobj); v = rb_time_unmagnify_to_rational(tobj->timew); if (!RB_TYPE_P(v, T_RATIONAL)) { v = rb_Rational1(v); } return v; }
Returns a string representation of self
, without subseconds:
t = Time.new(2000, 12, 31, 23, 59, 59, 0.5) t.to_s # => "2000-12-31 23:59:59 +0000"
Related: Time#ctime
, Time#inspect
:
t.ctime # => "Sun Dec 31 23:59:59 2000" t.inspect # => "2000-12-31 23:59:59.5 +000001"
static VALUE time_to_s(VALUE time) { struct time_object *tobj; GetTimeval(time, tobj); if (TZMODE_UTC_P(tobj)) return strftimev("%Y-%m-%d %H:%M:%S UTC", time, rb_usascii_encoding()); else return strftimev("%Y-%m-%d %H:%M:%S %z", time, rb_usascii_encoding()); }
Returns self.
static VALUE time_to_time(VALUE self) { return self; }
Returns true
if self
represents a Tuesday, false
otherwise:
t = Time.utc(2000, 1, 4) # => 2000-01-04 00:00:00 UTC t.tuesday? # => true
Related: Time#wednesday?
, Time#thursday?
, Time#friday?
.
static VALUE time_tuesday(VALUE time) { wday_p(2); }
Returns the number of microseconds in the subseconds part of self
in the range (0..999_999); lower-order digits are truncated, not rounded:
t = Time.now # => 2022-07-11 14:59:47.5484697 -0500 t.usec # => 548469
Related: Time#subsec
(returns exact subseconds).
Returns self
, converted to the UTC timezone:
t = Time.new(2000) # => 2000-01-01 00:00:00 -0600 t.utc? # => false t.utc # => 2000-01-01 06:00:00 UTC t.utc? # => true
Related: Time#getutc
(returns a new converted Time
object).
Returns true
if self
represents a time in UTC (GMT):
now = Time.now # => 2022-08-18 10:24:13.5398485 -0500 now.utc? # => false utc = Time.utc(2000, 1, 1, 20, 15, 1) # => 2000-01-01 20:15:01 UTC utc.utc? # => true
Related: Time.utc
.
static VALUE time_utc_p(VALUE time) { struct time_object *tobj; GetTimeval(time, tobj); return RBOOL(TZMODE_UTC_P(tobj)); }
Returns the offset in seconds between the timezones of UTC and self
:
Time.utc(2000, 1, 1).utc_offset # => 0 Time.local(2000, 1, 1).utc_offset # => -21600 # -6*3600, or minus six hours.
Returns the integer day of the week for self
, in range (0..6), with Sunday as zero.
t = Time.new(2000, 1, 2, 3, 4, 5, 6) # => 2000-01-02 03:04:05 +000006 t.wday # => 0 t.sunday? # => true
Related: Time#year
, Time#hour
, Time#min
.
static VALUE time_wday(VALUE time) { struct time_object *tobj; GetTimeval(time, tobj); MAKE_TM_ENSURE(time, tobj, tobj->vtm.wday != VTM_WDAY_INITVAL); return INT2FIX((int)tobj->vtm.wday); }
Returns true
if self
represents a Wednesday, false
otherwise:
t = Time.utc(2000, 1, 5) # => 2000-01-05 00:00:00 UTC t.wednesday? # => true
Related: Time#thursday?
, Time#friday?
, Time#saturday?
.
static VALUE time_wednesday(VALUE time) { wday_p(3); }
Returns a string which represents the time as a dateTime defined by XML Schema:
CCYY-MM-DDThh:mm:ssTZD CCYY-MM-DDThh:mm:ss.sssTZD
where TZD is Z or [+-]hh:mm.
If self is a UTC time, Z is used as TZD. [+-]hh:mm is used otherwise.
fraction_digits
specifies a number of digits to use for fractional seconds. Its default value is 0.
require 'time' t = Time.now t.iso8601 # => "2011-10-05T22:26:12-04:00"
You must require ‘time’ to use this method.
# File lib/time.rb, line 720 def xmlschema(fraction_digits=0) fraction_digits = fraction_digits.to_i s = strftime("%FT%T") if fraction_digits > 0 s << strftime(".%#{fraction_digits}N") end s << (utc? ? 'Z' : strftime("%:z")) end
Returns the integer day of the year of self
, in range (1..366).
Time.new(2000, 1, 1).yday # => 1 Time.new(2000, 12, 31).yday # => 366
static VALUE time_yday(VALUE time) { struct time_object *tobj; GetTimeval(time, tobj); MAKE_TM_ENSURE(time, tobj, tobj->vtm.yday != 0); return INT2FIX(tobj->vtm.yday); }
Returns the string name of the time zone for self
:
Time.utc(2000, 1, 1).zone # => "UTC" Time.new(2000, 1, 1).zone # => "Central Standard Time"
static VALUE time_zone(VALUE time) { struct time_object *tobj; VALUE zone; GetTimeval(time, tobj); MAKE_TM(time, tobj); if (TZMODE_UTC_P(tobj)) { return rb_usascii_str_new_cstr("UTC"); } zone = tobj->vtm.zone; if (NIL_P(zone)) return Qnil; if (RB_TYPE_P(zone, T_STRING)) zone = rb_str_dup(zone); return zone; }