2009-10-28 7 views
7

У меня есть строки вроде "84", "03" и т. Д., Которые я хочу преобразовать в объекты Date, но Date.new принимает только расширенный 4-значный год в качестве параметра. Я знаю, что это просто сделать, но я не хочу изобретать это колесо. Есть ли что-то, что делает это уже? Либо в стандартном Ruby, либо в ActiveSupport.Конвертировать двузначный год в четырехзначный год в Ruby

ответ

5

Выберите дату отсечения.

if year < cutoff, then year4 = "20" + year 
else year4 = "19" + year 

Кроме того, исправьте причину двухзначного года, иначе ваша система не будет совместима с Y2K +.

+1

Да, это то, что я закончил делать. Я просто хотел знать, есть ли какой-то удобный метод для этого в некоторой библиотеке. В качестве обрезания я использовал 70, потому что 1970 год - это эпоха Unix (http://en.wikipedia.org/wiki/Unix_time). – hsribei

0

Я не знаю такого компонента, и я не знаю, как вы его напишете; как бы он определил, какой двухзначный префикс использовать? Выбор одного вслепую имеет определенные продемонстрированные проблемы.

В зависимости от вашего приложения вы можете найти разумную эвристику для выбора между 19 и 20 для префикса, но проблема не разрешима вообще; информации недостаточно.

0

Действительно ли это имеет смысл? Когда вы перестанете рассматривать даты 19xx? Нет хорошего способа получить 4-значный год с последних 2-х цифр года.

+0

Если строка представляет собой день рождения, только что введенный на форме, и вам не нравились люди старше чем 99 ... да. Бывают случаи, когда это не совсем сумасшествие, я думаю, но это то, о чем вы хотите остановиться и сказать: «Я решаю здесь правильную проблему?» –

+0

Это вопрос, специфичный для приложения. Например, если ваше приложение имеет дело с записями, восходящими только к 1980 году, вы можете использовать это как свое обрезание. Или если это только прошлые данные, или будущее, или ... – derobert

+0

Изменение требований. Любое решение этой проблемы почти наверняка прорвется в течение года. –

4

Большинство двухзначных лет в прошлом, поэтому хорошим отключением для использования является 30. Например, если кто-то набирает '66, они, скорее всего, означают 1966. Фактически, это также обрезание, которое использует Excel, когда двузначная дата передается в ячейку даты.

У меня было приложение, которое принимало файлы с разделителями табуляции из электронных таблиц Excel, и они часто приходили с двузначными годами. Я написал эту обезьяну патч ActiveRecord, чтобы ActiveRecord обрабатывать две цифры года для полей даты:

class ActiveRecord::ConnectionAdapters::Column 
    class << self 
    protected 
    # If a year comes in with two digits, let's try to guess whether it's in the 
    # 20th or 21st century. Typically, Ruby pivots this decision around the 
    # year '69, but this is a bad guess. Since most of our dates will arrive in 
    # two digit format because of an Excel import, we should use the same pivot 
    # value that Excel uses. Excel pivots the decision around the year '30 
    # which seems to be a better guess anyway. 
    def new_date_with_two_digit_year_support(year, mon, mday) 
     year += 2000 if (0..29).include? year 
     year += 1900 if (30..99).include? year 
     new_date_without_two_digit_year_support(year, mon, mday) 
    end 
    alias_method_chain :new_date, :two_digit_year_support 
    end 
end 

Это не так, как родовое как то, что вопрос просил, но мы надеемся, что это помогает.

1

Если вы хотите, чтобы преобразовать 2 до 4 для будущих дат (например, форматирование кредитной карты Годен), вы можете попробовать:

$expYear = 12 

if (strlen($expYear) == 2) { 
    $expYear = substr(Date("Y"),0,2) . $expYear; 
} 

Это будет немного больше на будущее, поскольку он всегда получает текущий год Однако, если мы находимся на 95-м + году века .. это все равно вызовет проблемы c'est la vie