zakuro 0.5.0 → 0.6.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (63) hide show
  1. checksums.yaml +4 -4
  2. data/VERSION +1 -0
  3. data/lib/zakuro/calculation/base/gengou.rb +82 -0
  4. data/lib/zakuro/calculation/base/linear_gengou.rb +76 -0
  5. data/lib/zakuro/calculation/base/operated_year.rb +5 -15
  6. data/lib/zakuro/calculation/base/year.rb +26 -14
  7. data/lib/zakuro/calculation/gengou/internal/counter.rb +129 -0
  8. data/lib/zakuro/calculation/gengou/internal/reserve/interval.rb +183 -0
  9. data/lib/zakuro/calculation/gengou/internal/reserve/list.rb +382 -0
  10. data/lib/zakuro/calculation/gengou/internal/reserve.rb +42 -0
  11. data/lib/zakuro/calculation/gengou/scroll.rb +262 -0
  12. data/lib/zakuro/calculation/monthly/first_day.rb +3 -2
  13. data/lib/zakuro/calculation/monthly/month.rb +49 -2
  14. data/lib/zakuro/calculation/monthly/operated_month.rb +2 -2
  15. data/lib/zakuro/calculation/range/full_range.rb +65 -103
  16. data/lib/zakuro/calculation/range/operated_range.rb +13 -8
  17. data/lib/zakuro/calculation/range/operated_solar_terms.rb +36 -17
  18. data/lib/zakuro/calculation/range/transfer/gengou_scroller.rb +54 -0
  19. data/lib/zakuro/calculation/range/transfer/year_boundary.rb +25 -21
  20. data/lib/zakuro/calculation/specifier/single_day.rb +13 -35
  21. data/lib/zakuro/calculation/summary/single.rb +5 -2
  22. data/lib/zakuro/calculation/version/internal/crawler.rb +51 -0
  23. data/lib/zakuro/calculation/version/internal/range.rb +39 -0
  24. data/lib/zakuro/calculation/version/version.rb +24 -0
  25. data/lib/zakuro/era/japan/calendar.rb +133 -0
  26. data/lib/zakuro/era/japan/gengou/parser.rb +95 -25
  27. data/lib/zakuro/era/japan/gengou/type.rb +148 -41
  28. data/lib/zakuro/era/japan/gengou/validator.rb +157 -52
  29. data/lib/zakuro/era/japan/gengou/yaml/set-001-until-south.yaml +1870 -0
  30. data/lib/zakuro/era/japan/gengou/yaml/set-002-from-north.yaml +810 -0
  31. data/lib/zakuro/era/japan/gengou/yaml/set-003-modern.yaml +50 -0
  32. data/lib/zakuro/era/japan/gengou.rb +5 -5
  33. data/lib/zakuro/era/japan/version.rb +151 -0
  34. data/lib/zakuro/era/{western.rb → western/calendar.rb} +0 -0
  35. data/lib/zakuro/merchant.rb +12 -3
  36. data/lib/zakuro/operation/month/parser.rb +1 -1
  37. data/lib/zakuro/operation/month/type.rb +1 -1
  38. data/lib/zakuro/operation/month/validator.rb +1 -1
  39. data/lib/zakuro/output/response.rb +5 -5
  40. data/lib/zakuro/tools/typeconv.rb +38 -0
  41. data/lib/zakuro/tools/typeof.rb +4 -1
  42. data/lib/zakuro/version/context.rb +24 -3
  43. data/lib/zakuro/version/daien/daien.rb +1 -26
  44. data/lib/zakuro/version/genka/genka.rb +1 -26
  45. data/lib/zakuro/version/gihou/gihou.rb +1 -30
  46. data/lib/zakuro/version/gregorio/gregorio.rb +1 -9
  47. data/lib/zakuro/version/houryaku/houryaku.rb +1 -9
  48. data/lib/zakuro/version/joukyou/joukyou.rb +1 -9
  49. data/lib/zakuro/version/kansei/kansei.rb +1 -9
  50. data/lib/zakuro/version/senmyou/senmyou.rb +1 -30
  51. data/lib/zakuro/version/tenpou/tenpou.rb +1 -9
  52. data/zakuro.gemspec +1 -3
  53. metadata +25 -17
  54. data/lib/zakuro/calculation/base/multi_gengou.rb +0 -101
  55. data/lib/zakuro/calculation/base/multi_gengou_roller.rb +0 -218
  56. data/lib/zakuro/calculation/range/transfer/western_date_allocation.rb +0 -82
  57. data/lib/zakuro/era/japan/reki.rb +0 -91
  58. data/lib/zakuro/era/japan/yaml/set-001-until-south.yaml +0 -1121
  59. data/lib/zakuro/era/japan/yaml/set-002-from-north.yaml +0 -485
  60. data/lib/zakuro/era/japan/yaml/set-003-modern.yaml +0 -28
  61. data/lib/zakuro/version/abstract_version.rb +0 -29
  62. data/lib/zakuro/version.rb +0 -7
  63. data/lib/zakuro/version_factory.rb +0 -59
@@ -0,0 +1,382 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative '../../../../era/japan/gengou'
4
+ require_relative '../../../../era/japan/calendar'
5
+ require_relative '../../../../era/western/calendar'
6
+
7
+ require_relative '../counter'
8
+
9
+ # :nodoc:
10
+ module Zakuro
11
+ # :nodoc:
12
+ module Calculation
13
+ # :nodoc:
14
+ module Gengou
15
+ # :nodoc:
16
+ module Reserve
17
+ # List
18
+ #
19
+ # 予約元号一覧
20
+ #
21
+ class List
22
+ # TODO: refactor
23
+
24
+ # @return [Integer] 不正年
25
+ INVALID_YEAR = -1
26
+ # @return [Integer] 最大試行数
27
+ MAX_SEARCH_COUNT = 10_000
28
+ # @return [Integer] 最大月日数
29
+ MAX_MONTH_DAYS = 30
30
+
31
+ # @return [Symbol] メソッド名
32
+ attr_reader :method_name
33
+ # @return [Western::Calendar] 開始日
34
+ attr_reader :start_date
35
+ # @return [Western::Calendar] 終了日
36
+ attr_reader :end_date
37
+ # @return [Array<Japan::Gengou>] 予約元号一覧
38
+ attr_reader :list
39
+
40
+ #
41
+ # 初期化
42
+ #
43
+ # @param [True, False] first true:1行目元号, false:2行目元号
44
+ # @param [Western::Calendar] start_date 開始日
45
+ # @param [Western::Calendar] end_date 終了日
46
+ #
47
+ def initialize(first: true, start_date: Western::Calendar.new,
48
+ end_date: Western::Calendar)
49
+ @method_name = first ? :first_line : :second_line
50
+ @start_date = start_date
51
+ @end_date = end_date
52
+ @list = []
53
+
54
+ update
55
+ end
56
+
57
+ #
58
+ # 元号を取得する
59
+ #
60
+ # @param [Western::Calendar] western_date 西暦日
61
+ #
62
+ # @return [Gengou::Counter] 加算元号
63
+ #
64
+ def get(western_date: Western::Calendar.new)
65
+ @list.each do |gengou|
66
+ if gengou.include?(date: western_date)
67
+ return Gengou::Counter.new(gengou: gengou).clone
68
+ end
69
+ end
70
+
71
+ Gengou::Counter.new
72
+ end
73
+
74
+ #
75
+ # 範囲内元号を取得する
76
+ #
77
+ # 次のパターンが考えられる
78
+ # 1. 元号の開始日から終了日まで該当元号なし(無効な元号)
79
+ # 2. 元号の開始日までは該当元号なし(無効な元号、開始日以降の元号)
80
+ # 3. 元号の開始日と月初日が合致し、末日まで同一元号(開始日以降の元号のみ)
81
+ # 4. 月の途中で有効な元号が切り替わる(有効な元号、有効な元号...)
82
+ # 5. 途中から該当元号なし(開始日以降の元号、無効な元号)
83
+ #
84
+ # FIXME: 有効な元号、無効な元号、有効な元号のようなストライプのパターンに対応していない
85
+ #
86
+ # @param [Western::Calendar] start_date 西暦開始日
87
+ # @param [Western::Calendar] end_date 西暦終了日
88
+ #
89
+ # @return [Array<Gengou::Counter>] 範囲内元号
90
+ #
91
+ def collect(start_date: Western::Calendar.new, end_date: Western::Calendar.new)
92
+ result = []
93
+
94
+ # 開始チェック
95
+ current_gengou = get(western_date: start_date)
96
+ result.push(current_gengou)
97
+
98
+ ## 範囲内に次の有効元号があるか
99
+ if current_gengou.invalid?
100
+ current_gengou = proceed(western_date: start_date)
101
+
102
+ return result if suspend?(current_gengou: current_gengou, end_date: end_date)
103
+
104
+ result.push(current_gengou)
105
+ end
106
+
107
+ return result if suspend?(current_gengou: current_gengou, end_date: end_date)
108
+
109
+ # 有効元号チェック
110
+ continue(result: result, current_date: current_gengou.western_end_date.clone,
111
+ end_date: end_date)
112
+ end
113
+
114
+ #
115
+ # 元号を進めて取得する
116
+ #
117
+ # @param [Western::Calendar] western_date 西暦日
118
+ #
119
+ # @return [Gengou::Counter] 加算元号
120
+ #
121
+ def proceed(western_date: Western::Calendar.new)
122
+ current_gengou = get(western_date: western_date)
123
+
124
+ # 無効な元号
125
+ if current_gengou.invalid?
126
+ @list.each do |gengou|
127
+ next if gengou.invalid?
128
+
129
+ # すでに超過している場合
130
+ break if western_date > gengou.end_date
131
+
132
+ return Gengou::Counter.new(gengou: gengou).clone
133
+ end
134
+
135
+ return Gengou::Counter.new
136
+ end
137
+
138
+ # 有効な元号
139
+ @list.each do |gengou|
140
+ next if gengou.invalid?
141
+
142
+ if gengou.both_start_date.western > current_gengou.western_end_date
143
+ return Gengou::Counter.new(gengou: gengou).clone
144
+ end
145
+ end
146
+
147
+ Gengou::Counter.new
148
+ end
149
+
150
+ #
151
+ # 和暦開始日を取得する
152
+ #
153
+ # @return [Japan::Calendar] 和暦開始日
154
+ #
155
+ def japan_start_date
156
+ return Japan::Calendar.new if invalid?
157
+
158
+ @list[0].both_start_date.japan.clone
159
+ end
160
+
161
+ #
162
+ # 西暦開始日を取得する
163
+ #
164
+ # @return [Western::Calendar] 西暦開始日
165
+ #
166
+ def western_start_date
167
+ return Western::Calendar.new if invalid?
168
+
169
+ @list[0].both_start_date.western.clone
170
+ end
171
+
172
+ #
173
+ # 西暦開始年を取得する
174
+ #
175
+ # @return [Integer] 西暦開始年
176
+ #
177
+ def western_start_year
178
+ return INVALID_YEAR if invalid?
179
+
180
+ @list[0].both_start_year.western.clone
181
+ end
182
+
183
+ #
184
+ # 西暦終了年を取得する
185
+ #
186
+ # @return [Integer] 西暦終了年
187
+ #
188
+ def western_end_year
189
+ return INVALID_YEAR if invalid?
190
+
191
+ return INVALID_YEAR if @list.size.zero?
192
+
193
+ @list[-1].end_year
194
+ end
195
+
196
+ #
197
+ # 不正か
198
+ #
199
+ # @return [True] 不正
200
+ # @return [False] 不正なし
201
+ #
202
+ def invalid?
203
+ return true unless @list
204
+
205
+ return true if @list.size.zero?
206
+
207
+ false
208
+ end
209
+
210
+ private
211
+
212
+ #
213
+ # 予約元号一覧を更新する
214
+ #
215
+ def update
216
+ result = internal
217
+
218
+ return result if result.size.zero?
219
+
220
+ prev_gengou(list: result)
221
+
222
+ next_gengou(list: result)
223
+
224
+ @list = result
225
+ end
226
+
227
+ #
228
+ # 開始日・終了日に対応する予約元号一覧を取得する
229
+ #
230
+ # @return [Array<Japan::Gengou>] 予約元号一覧
231
+ #
232
+ def internal
233
+ current_gengou = line(date: start_date)
234
+ result = []
235
+
236
+ return result if current_gengou.invalid?
237
+
238
+ result.push(current_gengou)
239
+ (0..MAX_SEARCH_COUNT).each do |_index|
240
+ current_end_date = current_gengou.end_date.clone
241
+ break if current_end_date > end_date
242
+
243
+ current_gengou = line(date: current_end_date + 1)
244
+ result.push(current_gengou)
245
+ end
246
+
247
+ result
248
+ end
249
+
250
+ #
251
+ # 前の元号を設定する
252
+ #
253
+ # @note 開始日の30日前に前の元号がある場合は、前の元号を設定する
254
+ #
255
+ # @param [Array<Japan::Gengou>] list 元号一覧
256
+ #
257
+ def prev_gengou(list:)
258
+ return unless list
259
+
260
+ return if list.size.zero?
261
+
262
+ first_gengou_date = list[0].both_start_date.western.clone
263
+
264
+ border_date = start_date.clone - MAX_MONTH_DAYS
265
+
266
+ return if first_gengou_date < border_date
267
+
268
+ gengou = line(date: first_gengou_date - 1)
269
+
270
+ return if gengou.invalid?
271
+
272
+ list.unshift(gengou)
273
+ end
274
+
275
+ #
276
+ # 次の元号を設定する
277
+ #
278
+ # @note 開始日の30日後に次の元号がある場合は、次の元号を設定する
279
+ #
280
+ # @param [Array<Japan::Gengou>] list 元号一覧
281
+ #
282
+ def next_gengou(list:)
283
+ return unless list
284
+
285
+ return if list.size.zero?
286
+
287
+ last_gengou_date = list[-1].end_date.clone
288
+
289
+ border_date = end_date.clone + MAX_MONTH_DAYS
290
+
291
+ return if border_date < last_gengou_date
292
+
293
+ gengou = line(date: last_gengou_date + 1)
294
+
295
+ return if gengou.invalid?
296
+
297
+ list.push(gengou)
298
+ end
299
+
300
+ #
301
+ # 元号
302
+ #
303
+ # @param [Western::Calendar] date 日付
304
+ #
305
+ # @return [Japan::Gengou] 元号
306
+ #
307
+ def line(date:)
308
+ List.send(method_name, **{ date: date })
309
+ end
310
+
311
+ #
312
+ # 有効元号を継続する
313
+ #
314
+ # @param [Array<Gengou::Counter>] result 範囲内元号
315
+ # @param [Gengou::Counter] current_gengou 現在元号
316
+ # @param [Western::Calendar] end_date 終了日
317
+ #
318
+ # @return [Array<Gengou::Counter>] 範囲内元号
319
+ #
320
+ def continue(result:, current_date:, end_date:)
321
+ (0..MAX_SEARCH_COUNT).each do |_index|
322
+ current_gengou = proceed(western_date: current_date)
323
+
324
+ return result if suspend?(current_gengou: current_gengou, end_date: end_date)
325
+
326
+ # 範囲内元号
327
+ result.push(current_gengou)
328
+
329
+ current_date = current_gengou.western_end_date.clone
330
+ end
331
+
332
+ # 終了
333
+ result
334
+ end
335
+
336
+ #
337
+ # 中断する
338
+ #
339
+ # @param [Gengou::Counter] current_gengou 現在元号
340
+ # @param [Western::Calendar] end_date 終了日
341
+ #
342
+ # @return [True] 中断
343
+ # @return [False] 継続
344
+ #
345
+ def suspend?(current_gengou:, end_date:)
346
+ ## 有効元号なし
347
+ return true if current_gengou.invalid?
348
+
349
+ ## 範囲内元号なし
350
+ return true if current_gengou.western_start_date > end_date
351
+
352
+ false
353
+ end
354
+
355
+ #
356
+ # 1行目元号
357
+ #
358
+ # @param [Western::Calendar] date 日付
359
+ #
360
+ # @return [Japan::Gengou] 1行目元号
361
+ #
362
+ def self.first_line(date:)
363
+ Zakuro::Japan::GengouResource.first_line(date: date)
364
+ end
365
+ private_class_method :first_line
366
+
367
+ #
368
+ # 2行目元号
369
+ #
370
+ # @param [Western::Calendar] date 日付
371
+ #
372
+ # @return [Japan::Gengou] 2行目元号
373
+ #
374
+ def self.second_line(date:)
375
+ Zakuro::Japan::GengouResource.second_line(date: date)
376
+ end
377
+ private_class_method :second_line
378
+ end
379
+ end
380
+ end
381
+ end
382
+ end
@@ -0,0 +1,42 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative '../../../era/western/calendar'
4
+ require_relative './reserve/interval'
5
+ require_relative './reserve/list'
6
+
7
+ # :nodoc:
8
+ module Zakuro
9
+ # :nodoc:
10
+ module Calculation
11
+ # :nodoc:
12
+ module Gengou
13
+ # Reserve
14
+ #
15
+ # 元号に基づき計算範囲を予約する
16
+ #
17
+ module Reserve
18
+ #
19
+ # 予約結果を取得する
20
+ #
21
+ # * 開始日・終了日から計算する範囲を求める
22
+ # * 開始日・終了日の範囲内にある元号全てが対象となる
23
+ # * 元号に応じて計算範囲は変化する
24
+ # * 元号の開始日(改元日)が開始日よりも前であれば、結果開始日は前者になる
25
+ # * 元号の終了日(改元前日)が終了日よりも後であれば、結果終了日は前者になる
26
+ # * 南北朝のように複数元号に属する場合、より広い範囲の元号に合わせる
27
+ # * 属する元号よりもさらに範囲を広げる場合がある
28
+ # * 開始日が最初の元号の改元後30日以内の場合、さらに前の元号まで対象にする
29
+ # * 終了日が最後の元号の改元前日30日以内の場合、さらに次の元号まで対象にする
30
+ #
31
+ # @param [Western::Calendar] start_date 開始日
32
+ # @param [Western::Calendar] end_date 終了日
33
+ #
34
+ # @return [Interval] 予約済み計算範囲
35
+ #
36
+ def self.get(start_date: Western::Calendar.new, end_date: Western::Calendar.new)
37
+ Interval.new(start_date: start_date, end_date: end_date)
38
+ end
39
+ end
40
+ end
41
+ end
42
+ end
@@ -0,0 +1,262 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative '../../era/western/calendar'
4
+ require_relative '../base/gengou'
5
+ require_relative '../base/linear_gengou'
6
+ require_relative './internal/reserve/interval'
7
+
8
+ # :nodoc:
9
+ module Zakuro
10
+ # :nodoc:
11
+ module Calculation
12
+ # :nodoc:
13
+ module Gengou
14
+ # Scroll
15
+ #
16
+ # 元号スクロール
17
+ #
18
+ class Scroll
19
+ # @return [Western::Calendar] 月初日
20
+ attr_reader :monthly_start_date
21
+ # @return [Western::Calendar] 月末日
22
+ attr_reader :monthly_end_date
23
+ # @return [Reserve::Interval] 予約範囲
24
+ attr_reader :interval
25
+ # @return [Array<Counte>] 1行目元号
26
+ attr_reader :first_gengou
27
+ # @return [Array<Counte>] 2行目元号
28
+ attr_reader :second_gengou
29
+
30
+ #
31
+ # 初期化
32
+ #
33
+ # @param [Western::Calendar] start_date 西暦開始日(最大範囲)
34
+ # @param [Western::Calendar] end_date 西暦終了日(最大範囲)
35
+ #
36
+ def initialize(start_date: Western::Calendar.new, end_date: Western::Calendar.new)
37
+ @monthly_start_date = Western::Calendar.new
38
+ @monthly_end_date = Western::Calendar.new
39
+ @interval = Reserve::Interval.new(start_date: start_date, end_date: end_date)
40
+ @first_gengou = []
41
+ @second_gengou = []
42
+ @ignited = false
43
+ end
44
+
45
+ #
46
+ # 進める
47
+ #
48
+ # @param [Monthly::Month] month 月
49
+ #
50
+ def run(month:)
51
+ unless @ignited
52
+ # 開始日の検索を行う
53
+ @ignited = ignite(month: month)
54
+ return
55
+ end
56
+
57
+ # 時間を進める
58
+ advance(month: month)
59
+ end
60
+
61
+ #
62
+ # 元号開始を試みる
63
+ #
64
+ # @param [Monthly::Month] month 月
65
+ #
66
+ # @return [True] 開始あり
67
+ # @return [False] 開始なし
68
+ #
69
+ def ignite(month:)
70
+ return false unless ignitable?(month: month)
71
+
72
+ japan_start_date = @interval.japan_start_date
73
+
74
+ western_start_date = @interval.western_start_date
75
+
76
+ # 今月初日(和暦日が1月2日であれば、開始日の1日前が初日)
77
+ @monthly_start_date = western_start_date.clone - japan_start_date.day + 1
78
+
79
+ # 今月末
80
+ @monthly_end_date = @monthly_start_date.clone + month.days - 1
81
+
82
+ update_current_gengou
83
+
84
+ true
85
+ end
86
+
87
+ #
88
+ # 進める
89
+ #
90
+ # @param [Monthly::Month] month 月
91
+ #
92
+ def advance(month:)
93
+ @monthly_start_date = @monthly_end_date.clone + 1
94
+
95
+ @monthly_end_date = @monthly_start_date.clone + month.days - 1
96
+
97
+ next_year if month.number == 1 && !month.leaped?
98
+
99
+ update_current_gengou
100
+ end
101
+
102
+ #
103
+ # 共通の元号に変換する
104
+ #
105
+ # @return [Base::Gengou] 元号
106
+ #
107
+ def to_gengou
108
+ start_date = @monthly_start_date.clone
109
+ end_date = @monthly_end_date.clone
110
+
111
+ Base::Gengou.new(
112
+ start_date: start_date,
113
+ end_date: end_date,
114
+ first_line: to_linear_gengou(
115
+ start_date: start_date, end_date: end_date, gengou_list: @first_gengou
116
+ ),
117
+ second_line: to_linear_gengou(
118
+ start_date: start_date, end_date: end_date, gengou_list: @second_gengou
119
+ )
120
+ )
121
+ end
122
+
123
+ #
124
+ # 開始西暦年を取得する
125
+ #
126
+ # @return [Integer] 開始西暦年
127
+ #
128
+ def western_start_year
129
+ @interval.western_start_year
130
+ end
131
+
132
+ #
133
+ # 終了西暦年を取得する
134
+ #
135
+ # @return [Integer] 終了西暦年
136
+ #
137
+ def western_end_year
138
+ @interval.western_end_year
139
+ end
140
+
141
+ private
142
+
143
+ #
144
+ # 現在月に合わせて元号を更新する
145
+ #
146
+ def update_current_gengou
147
+ start_date = @monthly_start_date
148
+ end_date = @monthly_end_date
149
+ first_gengou = @interval.collect_first_gengou(start_date: start_date, end_date: end_date)
150
+ second_gengou = @interval.collect_second_gengou(start_date: start_date,
151
+ end_date: end_date)
152
+
153
+ @first_gengou = replace_gengou(source: @first_gengou, destination: first_gengou)
154
+ @second_gengou = replace_gengou(source: @second_gengou, destination: second_gengou)
155
+ end
156
+
157
+ #
158
+ # 元号を差し替える
159
+ #
160
+ # @param [Array<Counter>] source 元の元号
161
+ # @param [Array<Counter>] destination 次の元号
162
+ #
163
+ # @return [Array<Counter>] 差し替え結果
164
+ #
165
+ def replace_gengou(source: [], destination: [])
166
+ return destination if destination.size.zero?
167
+
168
+ return destination if source.size.zero?
169
+
170
+ last = source[-1]
171
+ destination[0] = last if destination[0].name == last.name
172
+
173
+ destination
174
+ end
175
+
176
+ #
177
+ # 直列元号に変換する
178
+ #
179
+ # * 最初の元号:開始日~その元号の終了日
180
+ # * 中間の元号:その元号の開始日~その元号の終了日
181
+ # * 最後の元号:その元号の開始日~終了日
182
+ #
183
+ # @param [Western::Calendar] start_date 西暦開始日
184
+ # @param [Western::Calendar] end_date 西暦終了日
185
+ # @param [Array<Counter>] gengou_list 元号リスト
186
+ #
187
+ # @return [Array<Base::Gengou>] 元号リスト
188
+ #
189
+ def to_linear_gengou(start_date:, end_date:, gengou_list: [])
190
+ return [] if gengou_list.size.zero?
191
+
192
+ result = []
193
+
194
+ gengou_list.each do |gengou|
195
+ if gengou.invalid?
196
+ # 無効元号は無効のままにする
197
+ result.push(Base::LinearGengou.new)
198
+ next
199
+ end
200
+
201
+ linear_gengou = to_limited_linear_gengou(
202
+ start_date: start_date,
203
+ end_date: end_date,
204
+ gengou: gengou
205
+ )
206
+ result.push(linear_gengou)
207
+ end
208
+
209
+ result
210
+ end
211
+
212
+ #
213
+ # 範囲を限定した直列元号に変換する
214
+ #
215
+ # * 開始日・終了日により範囲を狭める
216
+ #
217
+ # @param [Western::Calendar] start_date 西暦開始日
218
+ # @param [Western::Calendar] end_date 西暦終了日
219
+ # @param [Counter] gengou 加算元号
220
+ #
221
+ # @return [Base::Gengou] 元号
222
+ #
223
+ def to_limited_linear_gengou(start_date:, end_date:, gengou:)
224
+ gengou_start_date = gengou.western_start_date.clone
225
+ gengou_end_date = gengou.western_end_date.clone
226
+
227
+ gengou_start_date = start_date.clone if start_date > gengou_start_date
228
+ gengou_end_date = end_date.clone if end_date < gengou_end_date
229
+
230
+ Base::LinearGengou.new(
231
+ start_date: gengou_start_date, end_date: gengou_end_date,
232
+ name: gengou.name, year: gengou.japan_year
233
+ )
234
+ end
235
+
236
+ #
237
+ # 開始可能か
238
+ #
239
+ # @param [Monthly::Month] month 月
240
+ #
241
+ # @return [True] 開始可
242
+ # @return [True] 開始不可
243
+ #
244
+ def ignitable?(month:)
245
+ return false unless @monthly_start_date.invalid?
246
+
247
+ japan_start_date = @interval.japan_start_date
248
+
249
+ japan_start_date.same_month?(leaped: month.leaped?, month: month.number)
250
+ end
251
+
252
+ #
253
+ # 次年にする
254
+ #
255
+ def next_year
256
+ @first_gengou.each(&:next_year)
257
+ @second_gengou.each(&:next_year)
258
+ end
259
+ end
260
+ end
261
+ end
262
+ end
@@ -1,6 +1,6 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require_relative '../../era/western'
3
+ require_relative '../../era/western/calendar'
4
4
 
5
5
  # :nodoc:
6
6
  module Zakuro
@@ -23,7 +23,8 @@ module Zakuro
23
23
  # @param [Remainder] remainder 西暦日
24
24
  # @param [Western::Calendar] western_date 大余小余
25
25
  #
26
- def initialize(western_date: Western::Calendar.new, remainder:)
26
+ def initialize(western_date: Western::Calendar.new,
27
+ remainder: Calculation::Cycle::AbstractRemainder.new)
27
28
  # 西暦日
28
29
  @western_date = western_date
29
30
  # 大余小余