zakuro 0.0.0
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.
- checksums.yaml +7 -0
- data/.editorconfig +9 -0
- data/.gitignore +69 -0
- data/.rspec +3 -0
- data/.rubocop.yml +14 -0
- data/.travis.yml +6 -0
- data/Gemfile +19 -0
- data/LICENSE.txt +21 -0
- data/README.md +44 -0
- data/Rakefile +20 -0
- data/bin/console +14 -0
- data/bin/setup +8 -0
- data/images/12/346/234/210/344/273/245/351/231/215/343/201/256/345/205/245/345/256/232/346/260/227.png +0 -0
- data/images/12/346/234/210/344/273/245/351/231/215/343/201/256/346/234/210/343/201/256/351/200/262/351/200/200.png +0 -0
- data/images/source/description.numbers +0 -0
- data/images//345/205/245/345/256/232/346/260/227/343/201/256/350/265/267/347/256/227.png +0 -0
- data/images//345/220/204/346/234/210/343/201/256/346/261/202/343/202/201/346/226/271.png +0 -0
- data/images//345/244/252/351/231/275/343/201/250/346/234/210.png +0 -0
- data/lib/zakuro.rb +9 -0
- data/lib/zakuro/condition.rb +239 -0
- data/lib/zakuro/cycle/abstract_remainder.rb +457 -0
- data/lib/zakuro/cycle/zodiac.rb +103 -0
- data/lib/zakuro/era/gengou/set-001-until-south.yaml +375 -0
- data/lib/zakuro/era/gengou/set-002-from-north.yaml +166 -0
- data/lib/zakuro/era/gengou/set-003-modern.yaml +12 -0
- data/lib/zakuro/era/japan.rb +630 -0
- data/lib/zakuro/era/western.rb +412 -0
- data/lib/zakuro/merchant.rb +57 -0
- data/lib/zakuro/output/error.rb +10 -0
- data/lib/zakuro/output/logger.rb +64 -0
- data/lib/zakuro/output/response.rb +170 -0
- data/lib/zakuro/output/result.rb +219 -0
- data/lib/zakuro/output/stringifier.rb +62 -0
- data/lib/zakuro/version.rb +7 -0
- data/lib/zakuro/version/abstract_version.rb +29 -0
- data/lib/zakuro/version/genka/genka.rb +19 -0
- data/lib/zakuro/version/gihou/gihou.rb +19 -0
- data/lib/zakuro/version/gregorio/gregorio.rb +19 -0
- data/lib/zakuro/version/houryaku/houryaku.rb +19 -0
- data/lib/zakuro/version/joukyou/joukyou.rb +19 -0
- data/lib/zakuro/version/kansei/kansei.rb +19 -0
- data/lib/zakuro/version/senmyou/README.md +586 -0
- data/lib/zakuro/version/senmyou/base/era.rb +81 -0
- data/lib/zakuro/version/senmyou/base/gengou.rb +210 -0
- data/lib/zakuro/version/senmyou/base/remainder.rb +60 -0
- data/lib/zakuro/version/senmyou/base/solar_term.rb +66 -0
- data/lib/zakuro/version/senmyou/base/year.rb +58 -0
- data/lib/zakuro/version/senmyou/monthly/lunar_phase.rb +220 -0
- data/lib/zakuro/version/senmyou/monthly/month.rb +112 -0
- data/lib/zakuro/version/senmyou/senmyou.rb +34 -0
- data/lib/zakuro/version/senmyou/stella/lunar_orbit.rb +332 -0
- data/lib/zakuro/version/senmyou/stella/solar_average.rb +192 -0
- data/lib/zakuro/version/senmyou/stella/solar_orbit.rb +398 -0
- data/lib/zakuro/version/senmyou/stella/winter_solstice.rb +106 -0
- data/lib/zakuro/version/senmyou/summary/annual_data.rb +186 -0
- data/lib/zakuro/version/senmyou/summary/gengou_data.rb +294 -0
- data/lib/zakuro/version/taien/taien.rb +19 -0
- data/lib/zakuro/version/tenpou/tenpou.rb +19 -0
- data/lib/zakuro/version_factory.rb +59 -0
- data/zakuro.gemspec +31 -0
- metadata +106 -0
@@ -0,0 +1,457 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
# :nodoc:
|
4
|
+
module Zakuro
|
5
|
+
# :nodoc:
|
6
|
+
module Cycle
|
7
|
+
#
|
8
|
+
# 大余小余(時刻情報)
|
9
|
+
# @abstract 大余小余計算に必要な処理を行う、暦に依存しない汎用的なクラス
|
10
|
+
#
|
11
|
+
class AbstractRemainder # rubocop:disable Metrics/ClassLength
|
12
|
+
# @return [Integer] 大余上限
|
13
|
+
LIMIT = 60
|
14
|
+
|
15
|
+
# @return [Integer] 大余("日"に相当)
|
16
|
+
attr_reader :day
|
17
|
+
# @return [Integer] 小余("分"に相当)
|
18
|
+
attr_reader :minute
|
19
|
+
# @return [Integer] 秒
|
20
|
+
attr_reader :second
|
21
|
+
# @return [Integer] 繰り上げなしの小余
|
22
|
+
attr_reader :base_limit
|
23
|
+
# @return [Integer] 1大余に必要な小余(暦によって基数が異なる)
|
24
|
+
attr_reader :base_day
|
25
|
+
# @return [Integer] 1小余に必要な秒(暦によって基数が異なる)
|
26
|
+
attr_reader :base_minute
|
27
|
+
# 繰り上げ有無
|
28
|
+
# @return [True] 繰り上げあり
|
29
|
+
# @return [False] 繰り上げなし
|
30
|
+
attr_reader :limited
|
31
|
+
|
32
|
+
# :reek:instanceVariableAssumption
|
33
|
+
# rubocop:disable Metrics/ParameterLists
|
34
|
+
|
35
|
+
#
|
36
|
+
# 初期化
|
37
|
+
#
|
38
|
+
# @param [Integer] day 大余("日"に相当)
|
39
|
+
# @param [Integer] minute 小余("分"に相当)
|
40
|
+
# @param [Integer] second 秒
|
41
|
+
# @param [Integer] total 繰り上げなしの小余
|
42
|
+
# @param [Integer] base_day 1大余に必要な小余(暦によって基数が異なる)
|
43
|
+
# @param [Integer] base_mitune 1小余に必要な秒(暦によって基数が異なる)
|
44
|
+
#
|
45
|
+
def initialize(day: -1, minute: -1, second: -1, total: -1,
|
46
|
+
base_day:, base_mitune:)
|
47
|
+
@base_limit = LIMIT
|
48
|
+
@base_day = base_day
|
49
|
+
@base_minute = base_mitune
|
50
|
+
@limited = true
|
51
|
+
|
52
|
+
set(day: day, minute: minute, second: second, total: total)
|
53
|
+
end
|
54
|
+
# rubocop:enable Metrics/ParameterLists
|
55
|
+
|
56
|
+
#
|
57
|
+
# 値を設定する
|
58
|
+
#
|
59
|
+
# @param [Integer] day 大余("日"に相当)
|
60
|
+
# @param [Integer] minute 小余("分"に相当)
|
61
|
+
# @param [Integer] second 秒
|
62
|
+
# @param [Integer] total 繰り上げなしの小余
|
63
|
+
#
|
64
|
+
# @return [AbstractRemainder] 自身の参照
|
65
|
+
#
|
66
|
+
def set(day: -1, minute: -1, second: -1, total: -1)
|
67
|
+
@day = day
|
68
|
+
@minute = minute
|
69
|
+
@second = second
|
70
|
+
|
71
|
+
if total != -1
|
72
|
+
@day = (total.to_f / @base_day).floor
|
73
|
+
@minute = (total % @base_day)
|
74
|
+
@second = 0
|
75
|
+
end
|
76
|
+
|
77
|
+
self
|
78
|
+
end
|
79
|
+
|
80
|
+
#
|
81
|
+
# 繰り上げ処理を外す
|
82
|
+
#
|
83
|
+
# @return [AbstractRemainder] 自身の参照
|
84
|
+
#
|
85
|
+
def lift_limit
|
86
|
+
@limited = false
|
87
|
+
|
88
|
+
self
|
89
|
+
end
|
90
|
+
|
91
|
+
#
|
92
|
+
# 繰り上げ処理を設定する
|
93
|
+
#
|
94
|
+
# @return [AbstractRemainder] 自身の参照
|
95
|
+
#
|
96
|
+
def set_limit
|
97
|
+
@limited = true
|
98
|
+
|
99
|
+
self
|
100
|
+
end
|
101
|
+
|
102
|
+
#
|
103
|
+
# 無効かどうか
|
104
|
+
#
|
105
|
+
# @param [AbstractRemainder] param 自クラスのインスタンス(デフォルトは自身の参照)
|
106
|
+
#
|
107
|
+
# @return [True] 無効
|
108
|
+
# @return [False] 有効
|
109
|
+
#
|
110
|
+
def invalid?(param: self)
|
111
|
+
raise ArgumentError, 'unmatch parameter type' unless param.is_a?(AbstractRemainder)
|
112
|
+
|
113
|
+
param.day == -1 || param.minute == -1 || param.second == -1
|
114
|
+
end
|
115
|
+
|
116
|
+
#
|
117
|
+
# 十干十二支名
|
118
|
+
#
|
119
|
+
# @return [String] 十干十二支名
|
120
|
+
#
|
121
|
+
def zodiac_name
|
122
|
+
Cycle::Zodiac.day_name(day: @day)
|
123
|
+
end
|
124
|
+
|
125
|
+
#
|
126
|
+
# 日が同じ十干かどうか(大小の月判定)
|
127
|
+
#
|
128
|
+
# @param [Integer] other 大余
|
129
|
+
#
|
130
|
+
# @return [True] 当月朔日と翌月朔日が同じ十干(「大」の月)
|
131
|
+
# @return [False] 当月朔日と翌月朔日が異なる十干(「小」の月)
|
132
|
+
#
|
133
|
+
def same_remainder_divided_by_ten?(other:)
|
134
|
+
day = @day % LIMIT
|
135
|
+
|
136
|
+
(day % 10) == (other % 10)
|
137
|
+
end
|
138
|
+
|
139
|
+
#
|
140
|
+
# (非破壊的に)加算する
|
141
|
+
#
|
142
|
+
# @param [AbstractRemainder] other 他の大余小余
|
143
|
+
#
|
144
|
+
# @return [AbstractRemainder] 加算結果
|
145
|
+
#
|
146
|
+
def add(other)
|
147
|
+
invalid?(param: other)
|
148
|
+
day = @day + other.day
|
149
|
+
minute = @minute + other.minute
|
150
|
+
second = @second + other.second
|
151
|
+
day, minute, second = carry(day, minute, second)
|
152
|
+
|
153
|
+
clone.set(day: day, minute: minute, second: second)
|
154
|
+
end
|
155
|
+
|
156
|
+
#
|
157
|
+
# (破壊的に)加算する
|
158
|
+
#
|
159
|
+
# @param [AbstractRemainder] other 他の大余小余
|
160
|
+
#
|
161
|
+
# @return [AbstractRemainder] 加算結果
|
162
|
+
#
|
163
|
+
def add!(other)
|
164
|
+
result = add(other)
|
165
|
+
@day = result.day
|
166
|
+
@minute = result.minute
|
167
|
+
@second = result.second
|
168
|
+
|
169
|
+
self
|
170
|
+
end
|
171
|
+
|
172
|
+
#
|
173
|
+
# (非破壊的に)除算する
|
174
|
+
#
|
175
|
+
# @param [AbstractRemainder] other 他の大余小余
|
176
|
+
#
|
177
|
+
# @return [AbstractRemainder] 除算結果
|
178
|
+
#
|
179
|
+
def sub(other)
|
180
|
+
invalid?(param: other)
|
181
|
+
day = @day - other.day
|
182
|
+
minute = @minute - other.minute
|
183
|
+
second = @second - other.second
|
184
|
+
day, minute, second = carry(day, minute, second)
|
185
|
+
|
186
|
+
clone.set(day: day, minute: minute, second: second)
|
187
|
+
end
|
188
|
+
|
189
|
+
#
|
190
|
+
# (破壊的に)除算する
|
191
|
+
#
|
192
|
+
# @param [AbstractRemainder] other 他の大余小余
|
193
|
+
#
|
194
|
+
# @return [AbstractRemainder] 除算結果
|
195
|
+
#
|
196
|
+
def sub!(other)
|
197
|
+
result = sub(other)
|
198
|
+
@day = result.day
|
199
|
+
@minute = result.minute
|
200
|
+
@second = result.second
|
201
|
+
|
202
|
+
self
|
203
|
+
end
|
204
|
+
|
205
|
+
#
|
206
|
+
# 大小比較(>)
|
207
|
+
#
|
208
|
+
# @param [AbstractRemainder] other 他の大余小余
|
209
|
+
#
|
210
|
+
# @return [True] より大きい
|
211
|
+
# @return [False] 以下
|
212
|
+
#
|
213
|
+
def >(other)
|
214
|
+
up?(other)
|
215
|
+
end
|
216
|
+
|
217
|
+
#
|
218
|
+
# 大小比較(>=)
|
219
|
+
#
|
220
|
+
# @param [AbstractRemainder] other 他の大余小余
|
221
|
+
#
|
222
|
+
# @return [True] 以上
|
223
|
+
# @return [False] より小さい
|
224
|
+
#
|
225
|
+
def >=(other)
|
226
|
+
up?(other) || \
|
227
|
+
(@day == other.day && @minute == other.minute && @second == other.second)
|
228
|
+
end
|
229
|
+
|
230
|
+
#
|
231
|
+
# 大小比較(<)
|
232
|
+
#
|
233
|
+
# @param [AbstractRemainder] other 他の大余小余
|
234
|
+
#
|
235
|
+
# @return [True] より小さい
|
236
|
+
# @return [False] 以上
|
237
|
+
#
|
238
|
+
def <(other)
|
239
|
+
down?(other)
|
240
|
+
end
|
241
|
+
|
242
|
+
#
|
243
|
+
# 大小比較(<=)
|
244
|
+
#
|
245
|
+
# @param [AbstractRemainder] other 他の大余小余
|
246
|
+
#
|
247
|
+
# @return [True] 以下
|
248
|
+
# @return [False] より大きい
|
249
|
+
#
|
250
|
+
def <=(other)
|
251
|
+
down?(other) || \
|
252
|
+
(@day == other.day && @minute == other.minute && @second == other.second)
|
253
|
+
end
|
254
|
+
|
255
|
+
#
|
256
|
+
# 大小比較(==)
|
257
|
+
#
|
258
|
+
# @param [AbstractRemainder] other 他の大余小余
|
259
|
+
#
|
260
|
+
# @return [True] 等しい
|
261
|
+
# @return [False] 等しくない
|
262
|
+
#
|
263
|
+
def ==(other)
|
264
|
+
eql?(other)
|
265
|
+
end
|
266
|
+
|
267
|
+
#
|
268
|
+
# 大小比較(!=)
|
269
|
+
#
|
270
|
+
# @param [AbstractRemainder] other 他の大余小余
|
271
|
+
#
|
272
|
+
# @return [True] 等しくない
|
273
|
+
# @return [False] 等しい
|
274
|
+
#
|
275
|
+
def !=(other)
|
276
|
+
!eql?(other)
|
277
|
+
end
|
278
|
+
|
279
|
+
# 進朔
|
280
|
+
# @see 進朔 http://eco.mtk.nao.ac.jp/koyomi/wiki/C2C0B1A2C2C0CDDBCEF12FBFCABAF3.html
|
281
|
+
# 進朔とは、朔の瞬間が1日の3/4すなわち夕方以降となる場合に、その日ではなく1日進めて翌日を1日目にする方法のことです。
|
282
|
+
# 進朔するかどうかの基準時刻を進朔限といいます。宣明暦では1日8400分ですから、進朔限は6300分で、それ以降だと進朔されます。
|
283
|
+
|
284
|
+
#
|
285
|
+
# (非破壊的に)進朔する
|
286
|
+
#
|
287
|
+
# @see http://eco.mtk.nao.ac.jp/koyomi/wiki/C2C0B1A2C2C0CDDBCEF12FBFCABAF3.html
|
288
|
+
#
|
289
|
+
# 進朔とは、朔の瞬間が1日の3/4すなわち夕方以降となる場合に、その日ではなく1日進めて翌日を1日目にする方法のことです。
|
290
|
+
# 進朔するかどうかの基準時刻を進朔限といいます。宣明暦では1日8400分ですから、進朔限は6300分で、それ以降だと進朔されます。
|
291
|
+
#
|
292
|
+
# @return [AbstractRemainder] 進朔結果
|
293
|
+
#
|
294
|
+
def up_on_new_moon
|
295
|
+
cloned = clone
|
296
|
+
limit = (base_day * 3) / 4
|
297
|
+
if @minute >= limit
|
298
|
+
day, minute, second = carry((@day + 1), @minute, @second)
|
299
|
+
return cloned.set(day: day, minute: minute, second: second)
|
300
|
+
end
|
301
|
+
|
302
|
+
cloned
|
303
|
+
end
|
304
|
+
|
305
|
+
#
|
306
|
+
# (破壊的に)進朔する
|
307
|
+
#
|
308
|
+
# @see http://eco.mtk.nao.ac.jp/koyomi/wiki/C2C0B1A2C2C0CDDBCEF12FBFCABAF3.html
|
309
|
+
#
|
310
|
+
# 進朔とは、朔の瞬間が1日の3/4すなわち夕方以降となる場合に、その日ではなく1日進めて翌日を1日目にする方法のことです。
|
311
|
+
# 進朔するかどうかの基準時刻を進朔限といいます。宣明暦では1日8400分ですから、進朔限は6300分で、それ以降だと進朔されます。
|
312
|
+
#
|
313
|
+
# @return [AbstractRemainder] 進朔結果
|
314
|
+
#
|
315
|
+
def up_on_new_moon!
|
316
|
+
result = up_on_new_moon
|
317
|
+
@day = result.day
|
318
|
+
@minute = result.minute
|
319
|
+
@second = result.second
|
320
|
+
|
321
|
+
self
|
322
|
+
end
|
323
|
+
|
324
|
+
#
|
325
|
+
# 小余に揃えた結果を返す(秒は除外する)
|
326
|
+
#
|
327
|
+
# @return [Integer] 小余
|
328
|
+
#
|
329
|
+
def to_minute
|
330
|
+
@day * @base_day + @minute
|
331
|
+
end
|
332
|
+
|
333
|
+
#
|
334
|
+
# 大余に四捨五入した結果を返す(秒は除外する)
|
335
|
+
#
|
336
|
+
# @return [AbstractRemainder] 大余
|
337
|
+
#
|
338
|
+
def round
|
339
|
+
day = @day
|
340
|
+
day += 1 if @minute >= (@base_day / 2)
|
341
|
+
|
342
|
+
initialize(day, 0, 0)
|
343
|
+
end
|
344
|
+
|
345
|
+
#
|
346
|
+
# 文字化する
|
347
|
+
#
|
348
|
+
# @return [String] 文字化
|
349
|
+
#
|
350
|
+
def to_s
|
351
|
+
"大余(日): #{@day}, 小余(分): #{@minute}, 小余(秒): #{@second}"
|
352
|
+
end
|
353
|
+
|
354
|
+
#
|
355
|
+
# 特定の文字フォーマットにして出力する
|
356
|
+
#
|
357
|
+
# @param [String] form フォーマット(大余、小余、秒それぞれを%dで指定する)
|
358
|
+
#
|
359
|
+
# @return [String] フォーマットした結果
|
360
|
+
#
|
361
|
+
def format(form: '%d-%d')
|
362
|
+
return '' if invalid?
|
363
|
+
|
364
|
+
super(form, @day, @minute, @second)
|
365
|
+
end
|
366
|
+
|
367
|
+
private
|
368
|
+
|
369
|
+
def carry!(day, minute, second)
|
370
|
+
@day, @minute, @second = carry(day, minute, second)
|
371
|
+
|
372
|
+
self
|
373
|
+
end
|
374
|
+
|
375
|
+
# 繰り上げ、繰り下げ
|
376
|
+
def carry(param_day, param_minute, param_second)
|
377
|
+
# NOTE: 計算方法としてマイナスでも徐算・剰余算の結果をプラス同様に扱う
|
378
|
+
minute, second = carry_second(param_minute, param_second)
|
379
|
+
|
380
|
+
day, minute = carry_minute(param_day, minute)
|
381
|
+
|
382
|
+
day = carry_day(day, @limited)
|
383
|
+
|
384
|
+
[day, minute, second]
|
385
|
+
end
|
386
|
+
|
387
|
+
def carry_second(param_minute, param_second)
|
388
|
+
sign = param_second.negative? ? -1 : 1
|
389
|
+
abs = sign * param_second
|
390
|
+
minute = param_minute + (sign * (abs / @base_minute).floor)
|
391
|
+
second = sign * (abs % @base_minute)
|
392
|
+
|
393
|
+
if sign.negative?
|
394
|
+
second += @base_minute
|
395
|
+
minute -= 1
|
396
|
+
end
|
397
|
+
|
398
|
+
[minute, second]
|
399
|
+
end
|
400
|
+
|
401
|
+
def carry_minute(param_day, param_minute)
|
402
|
+
sign = param_minute.negative? ? -1 : 1
|
403
|
+
abs = sign * param_minute
|
404
|
+
|
405
|
+
day = param_day + (sign * (abs / @base_day).floor)
|
406
|
+
minute = sign * (abs % @base_day)
|
407
|
+
|
408
|
+
if sign.negative?
|
409
|
+
minute += @base_day
|
410
|
+
day -= 1
|
411
|
+
end
|
412
|
+
|
413
|
+
[day, minute]
|
414
|
+
end
|
415
|
+
|
416
|
+
def carry_day(day, limited)
|
417
|
+
sign = day.negative? ? -1 : 1
|
418
|
+
abs = sign * day
|
419
|
+
carried = sign * (abs % @base_limit) if limited
|
420
|
+
carried += @base_limit if sign.negative?
|
421
|
+
carried
|
422
|
+
end
|
423
|
+
|
424
|
+
def up?(other)
|
425
|
+
invalid?(param: other)
|
426
|
+
day = other.day
|
427
|
+
minute = other.minute
|
428
|
+
return true if @day > day
|
429
|
+
return false if @day < day
|
430
|
+
|
431
|
+
return true if @minute > minute
|
432
|
+
return false if @minute < minute
|
433
|
+
|
434
|
+
@second > other.second
|
435
|
+
end
|
436
|
+
|
437
|
+
def eql?(other)
|
438
|
+
invalid?(param: other)
|
439
|
+
|
440
|
+
(@day == other.day && @minute == other.minute && @second == other.second)
|
441
|
+
end
|
442
|
+
|
443
|
+
def down?(other)
|
444
|
+
invalid?(param: other)
|
445
|
+
day = other.day
|
446
|
+
minute = other.minute
|
447
|
+
return true if @day < day
|
448
|
+
return false if @day > day
|
449
|
+
|
450
|
+
return true if @minute < minute
|
451
|
+
return false if @minute > minute
|
452
|
+
|
453
|
+
@second < other.second
|
454
|
+
end
|
455
|
+
end
|
456
|
+
end
|
457
|
+
end
|