问题
I want to override the .. and ... operators in Ruby's Range.
Reason is, I'm working with infinite date ranges in the database. If you pull an infinty datetime out of Postgres, you get a Float::INFINITY in Ruby.
The problem with this is, I cannot use Float::INFINITY as the end of a range:
Date.today...Float::INFINITY
=> Wed, 02 Nov 2016...Infinity
DateTime.now...Float::INFINITY
# ArgumentError: bad value for range
Time.now...Float::INFINITY
# ArgumentError: bad value for range
... yet I use .. and ... syntax quite often in my code.
To even be able to construct the range, you need to use DateTime::Infinity.new instead:
Date.today...DateTime::Infinity.new
=> Wed, 02 Nov 2016...#<Date::Infinity:0x007fd82348c698 @d=1>
DateTime.now...DateTime::Infinity.new
=> Wed, 02 Nov 2016 12:57:07 +0000...#<Date::Infinity:0x007fd82348c698 @d=1>
Time.now...DateTime::Infinity.new
=> 2016-11-02 12:57:33 +0000...#<Date::Infinity:0x007fd82348c698 @d=1>
But I would need to do the the Float::INFINITY -> DateTime::Infinity.new conversion every time:
model.start_time...convert_infinity(model.end_time)
Is there a way I can override the .. and ... operators so that I can incorporate the conversion function and keep the syntactic sugar?
回答1:
I don't think that what you want to do is a correct way of solving such issue.
What I would suggest instead, is to simply override the end_date method in model:
def end_date
super == Float::INFINITY ? DateTime::Infinity.new : super
end
This basically says if end_date in db is Float::INFINITY return DateTime::Infinity.new as end_date, otherwise return what's in database.
回答2:
Ruby 2.6 introduces endless range, which can be used in this manner, for example:
(DateTime.now..)
(DateTime.now...)
This provides a new approach to answering this question. Hope it's useful for someone!
来源:https://stackoverflow.com/questions/40380603/how-can-i-override-the-and-operators-of-ruby-ranges-to-accept-floatinfi