Есть обходной путь для преобразования часового пояса. Но предполагается, что вы заранее знаете разницу во времени. Взгляните на следующий фрагмент:
mississippi = Time.local(2000,11,13,9,35) # 9:35 am CST
california = mississippi - 2*3600 # Минус два часа.
time1 = mississippi.strftime("%X CST") # 09:35:00 CST
time2 = california.strftime("%X PST") # 07:35:00 PST
Спецификатор %x
в методе strftime
просто выводит время в формате hh:mm:ss
.
7.23. Определение числа дней в месяце
В текущей версии Ruby еще нет встроенной функции для этой цели. Но ее можно без труда написать самостоятельно:
require 'date'
def month_days(month,year=Date.today.year)
mdays = [nil,31,28,31,30,31,30,31,31,30,31.30,31]
mdays[2] = 29 if Date.leap?(year)
mdays[month]
end
days = month_days(5) # 31 (May)
days = month_days(2,2000) # 29 (February 2000)
days = month_days(2,2100) # 28 (February 2000)
7.24. Разбиение месяца на недели
Представьте, что нужно разбить месяц на недели, например чтобы напечатать календарь. Эту задачу решает приведенный ниже код. Возвращаемый массив состоит из подмассивов, по семь элементов в каждом. При этом первому элементу каждого внутреннего массива соответствует воскресенье. Начальные элементы для первой недели и конечные для второй могут быть равны nil
.
def calendar(month,year)
days = month_days(month,year)
t = Time.mktime(year,month,1)
first = t.wday
list = *1..days
weeks = [[]]
week1 = 7 - first
week1.times { weeks[0] << list.shift }
nweeks = list.size/7 + 1
nweeks.times do |i|
weeks[i+1] ||= []
7.times do
break if list.empty?
weeks[i+1] << list.shift
end
end
pad_first = 7-weeks[0].size
pad_first.times { weeks[0].unshift(nil) }
pad_last = 7-weeks[0].size
pad_last.times { weeks[-1].unshift(nil) }
weeks
end
arr = calendar(12,2008) # [[nil, 1, 2, 3, 4, 5, 6],
# [7, 8, 9, 10, 11, 12, 13],
# [14, 15, 16, 17, 18, 19, 20],
# [21, 22, 23, 24, 25, 26, 27],
# [28, 29, 30, 31, nil, nil, nil]]
Чтобы было понятнее, распечатаем этот массив массивов:
def print_calendar(month,year)
weeks = calendar(month,year)
weeks.each do |wk|
wk.each do |d|
item = d.nil? ? " "*4 : " %2d " % d
print item
end
puts
end
puts
end
# Выводится:
# 1 2 3 4 5 6
# 7 8 9 10 11 12 13
# 14 15 16 17 18 19 20
# 21 22 23 24 25 26 27
# 28 29 30 31
В этой главе мы рассмотрели класс Time
, который является оберткой для функций из стандартной библиотеки языка С. Были показаны его возможности и ограничения.
Мы также узнали, зачем существуют классы Date
и DateTime
и какую функциональность они предоставляют. Мы научились выполнять преобразования между этими классами и добавили несколько собственных полезных методов.
На этом обсуждение даты и времени завершается. Переходим к массивам, хэшам и другим перечисляемым структурам в Ruby.
Глава 8. Массивы, хэши и другие перечисляемые структуры
Все детали должны соединяться без усилий. Помните, что механизм, который вы пытаетесь собрать, вами же был и разобран.
Если не удается соединить детали, на то должна быть причина.
Ни в коем случае не пользуйтесь молотком.
Руководство по техническому обслуживанию компании IBM (1925)
Простых переменных для практического программирования недостаточно. В любом современном языке поддерживаются более сложные виды структурированных данных и предоставляются механизмы для создания новых абстрактных типов данных.
Исторически самой первой и широко распространившейся составной структурой данных был массив. Давным-давно, еще в языке ФОРТРАН, массивы назывались индексированными переменными; сегодня они несколько видоизменились, но основная идея во всех языках одна и та же.
Относительно недавно очень популярной структурой стали хэши. Как и массив, хэш представляет собой индексированный набор данных. Но, в отличие от массива, в качестве индекса может выступать любой объект. (В Ruby, как и в большинстве других языков, элементы массива индексируются числами.)
Наконец, мы рассмотрим сам модуль Enumerable
и разберемся, как он работает. И массивы, и хэши подмешивают этот модуль. То же самое может сделать и любой другой класс, которому необходима аналогичная функциональность. Но не будем забегать вперед. Начнем с массивов.
В Ruby массивы индексируются целыми числами; индексация начинается с нуля, как в языке С. На этом, впрочем, сходство и заканчивается.
Читать дальше
Конец ознакомительного отрывка
Купить книгу