zakuro 0.1.1 → 0.1.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -7,6 +7,7 @@ require_relative '../base/solar_term'
7
7
  require_relative '../monthly/lunar_phase'
8
8
  require_relative '../stella/solar_orbit'
9
9
  require_relative '../stella/solar_average'
10
+ require_relative '../stella/solar_location'
10
11
  require_relative '../stella/lunar_orbit'
11
12
 
12
13
  # :nodoc:
@@ -68,15 +69,13 @@ module Zakuro
68
69
 
69
70
  apply_big_and_small_of_the_month(annual_range: annual_range)
70
71
 
71
- SolarAverage.set_solar_terms_into_annual_range(western_year: western_year,
72
- annual_range: annual_range)
72
+ solar_average = SolarAverage.new(western_year: western_year)
73
+ solar_average.set(annual_range: annual_range)
73
74
 
74
75
  # 月間隔を取得するためだけの末尾要素を削除
75
76
  annual_range.pop
76
77
 
77
- adjust_leap_month(annual_range: annual_range)
78
-
79
- annual_range
78
+ initialize_month_label(annual_range: annual_range)
80
79
  end
81
80
 
82
81
  #
@@ -93,7 +92,7 @@ module Zakuro
93
92
  remainder: winter_solstice_age
94
93
  )
95
94
  solar_term = \
96
- SolarOrbit.calc_solar_term_by_remainder(
95
+ SolarLocation.get(
97
96
  solar_term: solar_term
98
97
  )
99
98
 
@@ -118,22 +117,17 @@ module Zakuro
118
117
  result = []
119
118
  lunar_phase = LunarPhase.new(western_year: western_year)
120
119
 
121
- is_last_year = true
122
-
123
- monthes = [11, 12] + [*1..12]
124
-
125
- monthes.each do |month|
126
- LOGGER.debug('---', "month: #{month}", "is_last_year: #{is_last_year}")
127
-
120
+ # 14ヶ月分を生成する(閏年で最大13ヶ月 + 末月の大小/二十四節気を求めるために必要な月)
121
+ (0..13).each do |_index|
128
122
  adjusted = lunar_phase.next_month
129
123
 
130
124
  result.push(
131
- InitializedMonth.new(month_label: MonthLabel.new(number: month),
125
+ InitializedMonth.new(month_label: MonthLabel.new,
132
126
  first_day: FirstDay.new(remainder: adjusted),
133
- is_last_year: is_last_year, phase_index: 0)
127
+ phase_index: 0)
134
128
  )
135
- is_last_year = false if month == 12
136
129
  end
130
+
137
131
  result
138
132
  end
139
133
  private_class_method :initialized_annual_range
@@ -144,41 +138,22 @@ module Zakuro
144
138
  # @param [Array<Month>] annual_range 1年データ
145
139
  #
146
140
  def self.apply_big_and_small_of_the_month(annual_range:)
147
- annual_range.each_with_index do |range, index|
148
- # 最後は比較対象がないためスキップする(=計算外の余分な月が最後に必要である)
149
- next if index == annual_range.size - 1
150
-
151
- next_month = annual_range[index + 1]
152
- range.eval_many_days(next_month_day: next_month.remainder.day)
141
+ # NOTE: 最後の月は処理できない(=計算外の余分な月が最後に必要である)
142
+ annual_range.each_cons(2) do |(current_month, next_month)|
143
+ current_month.eval_many_days(next_month_day: next_month.remainder.day)
153
144
  end
154
145
  end
155
146
  private_class_method :apply_big_and_small_of_the_month
156
147
 
157
- # :reek:TooManyStatements { max_statements: 10 }
158
-
159
148
  #
160
- # 閏月が存在した場合に以降の月を1つずつ減らす
161
- # @example 7,8,9 と続く月の8月が閏の場合、7, 閏7, 8 となる
149
+ # 月表示情報を更新する
162
150
  #
163
151
  # @param [Array<Month>] annual_range 1年データ
164
152
  #
165
- def self.adjust_leap_month(annual_range:)
166
- # 閏による月の再調整を行う
167
- leaped = false
168
- annual_range.each_with_index do |month, index|
169
- month.eval_leaped
170
- # NOTE: 初回閏月(閏11月)は前回月が存在しないため調整外
171
- leaped = true if month.leaped? && !index.zero?
172
-
173
- next unless leaped
174
-
175
- # NOTE: 常気法では閏月は2-3年に一度のため、1年に二度発生しない前提
176
-
177
- # 閏の分だけ1ヶ月ずらす
178
- month.back_to_last_month
179
- end
153
+ def self.initialize_month_label(annual_range:)
154
+ annual_range.each(&:rename_month_label_by_solar_term)
180
155
  end
181
- private_class_method :adjust_leap_month
156
+ private_class_method :initialize_month_label
182
157
  end
183
158
  end
184
159
  end
@@ -4,6 +4,8 @@ require_relative '../base/multi_gengou_roller'
4
4
 
5
5
  require_relative '../../../era/western'
6
6
  require_relative './annual_range'
7
+ require_relative './year_boundary'
8
+ require_relative './western_date_allocation'
7
9
 
8
10
  require_relative '../base/year'
9
11
 
@@ -11,6 +13,9 @@ require_relative '../base/year'
11
13
  module Zakuro
12
14
  # :nodoc:
13
15
  module Senmyou
16
+ # :reek:TooManyInstanceVariables { max_instance_variables: 5 }
17
+
18
+ #
14
19
  # FullRange 完全範囲
15
20
  # ある日からある日の範囲を計算可能な年月範囲
16
21
  # * 前提として元号年はその元号の開始年から数える
@@ -21,6 +26,7 @@ module Zakuro
21
26
  # * 元旦を基準にした時の正しい元号を設定している
22
27
  # * 引き当てたい日付が元旦ではない場合、その月日に従い元号を再度求める
23
28
  # * この再計算が必要になるのは、元号が切り替わる年のみである
29
+ #
24
30
  class FullRange
25
31
  # @return [Western::Calendar] 開始日
26
32
  attr_reader :start_date
@@ -70,36 +76,14 @@ module Zakuro
70
76
  def get
71
77
  return [] if invalid?
72
78
 
73
- pre_get
74
-
75
- years = FullRange.rearranged_years(annual_ranges: annual_ranges)
79
+ years = YearBoundary.get(annual_ranges: annual_ranges)
76
80
  years = update_gengou(years: years)
77
- years = update_first_day(years: years)
78
81
 
79
- post_get
82
+ WesternDateAllocation.update_first_day(years: years)
80
83
 
81
84
  years
82
85
  end
83
86
 
84
- #
85
- # 取得前処理
86
- #
87
- def pre_get
88
- # FIXME: 別インスタンス変数を定義する方法は改善したい(ディープコピーにするか、get再取得を廃止するか)
89
- @new_year_date_ = @new_year_date.clone
90
- @multi_gengou_roller_ = @multi_gengou_roller.clone
91
- end
92
-
93
- #
94
- # 取得前処理
95
- #
96
- # 再取得に備えて、カウントアップした日付を元に戻す
97
- #
98
- def post_get
99
- @new_year_date = @new_year_date_
100
- @multi_gengou_roller = @multi_gengou_roller_
101
- end
102
-
103
87
  # :reek:TooManyStatements { max_statements: 6 }
104
88
 
105
89
  #
@@ -123,24 +107,6 @@ module Zakuro
123
107
  years
124
108
  end
125
109
 
126
- #
127
- # 完全範囲内の年データの開始月を変更する
128
- #
129
- # @param [Array<Year>] annual_ranges 年データ(冬至基準)
130
- #
131
- # @return [Array<Year>] 年データ(元旦基準)
132
- #
133
- def self.rearranged_years(annual_ranges:)
134
- years = []
135
-
136
- (0..(annual_ranges.size - 2)).each do |index|
137
- year = rearranged_year(annual_ranges: annual_ranges, index: index)
138
- years.push(year)
139
- end
140
-
141
- years
142
- end
143
-
144
110
  # :reek:TooManyStatements { max_statements: 8 }
145
111
 
146
112
  #
@@ -168,102 +134,6 @@ module Zakuro
168
134
  updated_years
169
135
  end
170
136
 
171
- #
172
- # 月初日の西暦日を更新する
173
- #
174
- # @param [Array<Year>] years 完全範囲(月初日なし)
175
- #
176
- # @return [Array<Year>] 完全範囲(月初日あり)
177
- #
178
- def update_first_day(years:)
179
- # TODO: リファクタリング
180
-
181
- result = []
182
-
183
- years.each do |year|
184
- new_year_date = year.new_year_date.clone
185
- date = new_year_date.clone
186
-
187
- months = []
188
- year.months.each do |month|
189
- first_day = month.first_day
190
- updated_month = Month.new(
191
- month_label: month.month_label,
192
- first_day: FirstDay.new(remainder: first_day.remainder,
193
- western_date: date),
194
- solar_terms: month.solar_terms
195
- )
196
- months.push(updated_month)
197
-
198
- date = date.clone + updated_month.days
199
- end
200
-
201
- updated_year = Year.new(
202
- multi_gengou: year.multi_gengou, new_year_date: new_year_date,
203
- months: months, total_days: year.total_days
204
- )
205
-
206
- result.push(updated_year)
207
- end
208
-
209
- result
210
- end
211
-
212
- #
213
- # 当年データを生成する
214
- #
215
- # @param [Array<Year>] annual_ranges 年データ(冬至基準)
216
- # @param [Year] year 対象年
217
- #
218
- # @return [Year] 当年月ありの対象年
219
- #
220
- def self.push_current_year(annual_range:, year: Year.new)
221
- annual_range.each do |month|
222
- next if month.is_last_year
223
-
224
- year.push(month: month)
225
- end
226
-
227
- year
228
- end
229
-
230
- #
231
- # 昨年データを生成する
232
- #
233
- # @param [Array<Year>] annual_ranges 年データ(冬至基準)
234
- # @param [Year] year 対象年
235
- #
236
- # @return [Year] 昨年月ありの対象年
237
- #
238
- def self.push_last_year(annual_range:, year: Year.new)
239
- annual_range.each do |month|
240
- next unless month.is_last_year
241
-
242
- year.push(month: month)
243
- end
244
-
245
- year
246
- end
247
-
248
- #
249
- # 年データの開始月を変更する
250
- #
251
- # @param [Array<Year>] annual_ranges 年データ(冬至基準)
252
- # @param [Integer] index 対象年の要素番号
253
- #
254
- # @return [Year] 年データ(元旦基準)
255
- #
256
- def self.rearranged_year(annual_ranges:, index:)
257
- current_annual_range = annual_ranges[index]
258
- next_annual_range = annual_ranges[index + 1]
259
-
260
- year = push_current_year(annual_range: current_annual_range)
261
- push_last_year(annual_range: next_annual_range, year: year)
262
-
263
- year
264
- end
265
- private_class_method :rearranged_year
266
-
267
137
  private
268
138
 
269
139
  #
@@ -0,0 +1,68 @@
1
+ # frozen_string_literal: true
2
+
3
+ # :nodoc:
4
+ module Zakuro
5
+ # :nodoc:
6
+ module Senmyou
7
+ #
8
+ # WesternDateAllocation 西暦日の割り当て
9
+ #
10
+ module WesternDateAllocation
11
+ #
12
+ # 月初日の西暦日を更新する
13
+ #
14
+ # @param [Array<Year>] years 完全範囲(月初日なし)
15
+ #
16
+ # @return [Array<Year>] 完全範囲(月初日あり)
17
+ #
18
+ def self.get(years:)
19
+ update_first_day(years: years)
20
+
21
+ years
22
+ end
23
+
24
+ #
25
+ # 月初日の西暦日を更新する
26
+ #
27
+ # @param [Array<Year>] years 完全範囲(月初日なし)
28
+ #
29
+ def self.update_first_day(years:)
30
+ years.each_with_index do |year, index|
31
+ new_year_date = year.new_year_date.clone
32
+
33
+ months = year.months
34
+ update_first_day_within_all_months(
35
+ new_year_date: new_year_date, months: months
36
+ )
37
+
38
+ years[index] = Year.new(
39
+ multi_gengou: year.multi_gengou, new_year_date: new_year_date,
40
+ months: months, total_days: year.total_days
41
+ )
42
+ end
43
+ end
44
+
45
+ #
46
+ # 全ての月で月初日の西暦日を更新する
47
+ #
48
+ # @param [Western::Calendar] new_year_date 元旦
49
+ # @param [Array<Month>] months 月データ
50
+ #
51
+ def self.update_first_day_within_all_months(new_year_date:, months:)
52
+ date = new_year_date.clone
53
+ months.each_with_index do |month, index|
54
+ updated_month = Month.new(
55
+ month_label: month.month_label,
56
+ first_day: FirstDay.new(remainder: month.first_day.remainder,
57
+ western_date: date),
58
+ solar_terms: month.solar_terms
59
+ )
60
+ months[index] = updated_month
61
+
62
+ date = date.clone + updated_month.days
63
+ end
64
+ end
65
+ private_class_method :update_first_day_within_all_months
66
+ end
67
+ end
68
+ end
@@ -0,0 +1,138 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative '../base/multi_gengou_roller'
4
+
5
+ require_relative '../../../era/western'
6
+ require_relative './annual_range'
7
+
8
+ require_relative '../base/year'
9
+
10
+ # :nodoc:
11
+ module Zakuro
12
+ # :nodoc:
13
+ module Senmyou
14
+ #
15
+ # YearBoundary 年境界
16
+ #
17
+ module YearBoundary
18
+ #
19
+ # 年間範囲内の年データの開始月を変更する
20
+ #
21
+ # @param [Array<Year>] annual_ranges 年データ(冬至基準)
22
+ #
23
+ # @return [Array<Year>] 年データ(元旦基準)
24
+ #
25
+ def self.get(annual_ranges:)
26
+ categorize(annual_ranges: annual_ranges)
27
+ rearranged_years(annual_ranges: annual_ranges)
28
+ end
29
+
30
+ #
31
+ # 年間範囲内の年データの開始月を変更する
32
+ #
33
+ # @param [Array<Year>] annual_ranges 年データ(冬至基準)
34
+ #
35
+ # @return [Array<Year>] 年データ(元旦基準)
36
+ #
37
+ def self.rearranged_years(annual_ranges:)
38
+ years = []
39
+
40
+ (0..(annual_ranges.size - 2)).each do |index|
41
+ year = rearranged_year(annual_ranges: annual_ranges, index: index)
42
+ years.push(year)
43
+ end
44
+
45
+ years
46
+ end
47
+ private_class_method :rearranged_years
48
+
49
+ #
50
+ # 年間範囲を昨年/今年で分類する
51
+ #
52
+ # @param [Array<Year>] annual_range 1年データ
53
+ #
54
+ def self.categorize(annual_ranges:)
55
+ annual_ranges.each do |annual_range|
56
+ categorize_year(annual_range: annual_range)
57
+ end
58
+ end
59
+ private_class_method :categorize
60
+
61
+ #
62
+ # 各月を昨年/今年で分類する
63
+ #
64
+ # @param [Array<Month>] annual_range 1年データ
65
+ #
66
+ def self.categorize_year(annual_range:)
67
+ is_last_year = true
68
+ annual_range.each_with_index do |month, index|
69
+ is_last_year = false if month.number == 1
70
+
71
+ annual_range[index] = InitializedMonth.new(
72
+ month_label: month.month_label, first_day: month.first_day,
73
+ solar_terms: month.solar_terms, phase_index: month.phase_index,
74
+ is_last_year: is_last_year
75
+ )
76
+ end
77
+ end
78
+ private_class_method :categorize_year
79
+
80
+ #
81
+ # 年データの開始月を変更する
82
+ #
83
+ # @param [Array<Year>] annual_ranges 年データ(冬至基準)
84
+ # @param [Integer] index 対象年の要素番号
85
+ #
86
+ # @return [Year] 年データ(元旦基準)
87
+ #
88
+ def self.rearranged_year(annual_ranges:, index:)
89
+ current_annual_range = annual_ranges[index]
90
+ next_annual_range = annual_ranges[index + 1]
91
+
92
+ year = push_current_year(annual_range: current_annual_range)
93
+ push_last_year(annual_range: next_annual_range, year: year)
94
+
95
+ year
96
+ end
97
+ private_class_method :rearranged_year
98
+
99
+ #
100
+ # 当年データを生成する
101
+ #
102
+ # @param [Array<Year>] annual_ranges 年データ(冬至基準)
103
+ # @param [Year] year 対象年
104
+ #
105
+ # @return [Year] 当年月ありの対象年
106
+ #
107
+ def self.push_current_year(annual_range:, year: Year.new)
108
+ annual_range.each do |month|
109
+ next if month.is_last_year
110
+
111
+ year.push(month: month)
112
+ end
113
+
114
+ year
115
+ end
116
+ private_class_method :push_current_year
117
+
118
+ #
119
+ # 昨年データを生成する
120
+ #
121
+ # @param [Array<Year>] annual_ranges 年データ(冬至基準)
122
+ # @param [Year] year 対象年
123
+ #
124
+ # @return [Year] 昨年月ありの対象年
125
+ #
126
+ def self.push_last_year(annual_range:, year: Year.new)
127
+ annual_range.each do |month|
128
+ next unless month.is_last_year
129
+
130
+ year.push(month: month)
131
+ end
132
+
133
+ year
134
+ end
135
+ private_class_method :push_last_year
136
+ end
137
+ end
138
+ end