teratail header banner
teratail header banner
質問するログイン新規登録

回答編集履歴

13

テキスト追加

2021/11/27 19:44

投稿

退会済みユーザー
answer CHANGED
@@ -110,7 +110,7 @@
110
110
  ```
111
111
  とあるとおり、diff の第三引数に true を渡すと、小数点以下ありの数値が返ってきます。この小数部分を日数に換算することを考えます。
112
112
 
113
- - ご例示の、d1=`"2021-6-1"` と d2=`"2021-7-15"` であれば、`d2.diff(d1,'month', true)` は、私の手元の環境では
113
+ - ご例示の、dateFrom:`"2021-6-1"` と dateTo:`"2021-7-15"` であれば、`d2.diff(d1,'month', true)` は、私の手元の環境では
114
114
  1.4516129032258065
115
115
  という数を返しました。
116
116
 

12

テキスト追加

2021/11/27 19:44

投稿

退会済みユーザー
answer CHANGED
@@ -95,7 +95,7 @@
95
95
  ```javascript
96
96
  const [n, k] = monthDiff_md("2021-6-1","2021-7-15");
97
97
 
98
- console.log(n, k);
98
+ console.log([n, k]);
99
99
  ```
100
100
  出力結果:
101
101
  > [ 1, 14 ]

11

テキスト追加

2021/11/27 19:32

投稿

退会済みユーザー
answer CHANGED
@@ -114,7 +114,7 @@
114
114
  1.4516129032258065
115
115
  という数を返しました。
116
116
 
117
- - これの小数部分`r` = 0.4516129032258065 を日数に換算するために、この 0.45・・・に何を掛ければよいかというと、上記のソースコードに出てくる`d3` と `d4` の日数差です。この差は月でいえば一ヶ月ですが、日数換算だと`d3`の月の月末が何日なのかによって変わります。このへんを任せられるのがdayjsの強みですね
117
+ - これの小数部分`r` = 0.4516129032258065 を日数に換算するために、この 0.45・・・に何を掛ければよいかというと、上記のソースコードに出てくる`d3` と `d4` の日数差です。この差は月でいえば一ヶ月ですが、日数換算だと`d3`の月の月末が何日なのかによって変わります。また2月だったら年が閏年かも考慮しなければなりませんが、このへんを任せられるのがdayjsの強みですね
118
118
 
119
119
  - `d3` と `d4` の日数差を `m` として得て、`m`に先の小数 `r` = 0.45・・・ を乗じると、欲しい剰余日数が出るはずですが、計算結果としては整数にごく近い小数になると思います。私の手元では、
120
120
  14.000000000000002

10

テキスト追加

2021/11/27 14:57

投稿

退会済みユーザー
answer CHANGED
@@ -118,4 +118,4 @@
118
118
 
119
119
  - `d3` と `d4` の日数差を `m` として得て、`m`に先の小数 `r` = 0.45・・・ を乗じると、欲しい剰余日数が出るはずですが、計算結果としては整数にごく近い小数になると思います。私の手元では、
120
120
  14.000000000000002
121
- となりました。これの小数を Math.round で切り捨てれば、得たい剰余日数の14が得られます。
121
+ となりました。これの小数を Math.round で切り捨て(または切り上げ)れば、得たい剰余日数の14が得られます。

9

テキスト追加

2021/11/27 14:49

投稿

退会済みユーザー
answer CHANGED
@@ -71,7 +71,7 @@
71
71
  const d1 = dayjs(dateFrom, 'YYYY-M-D');
72
72
  const d2 = dayjs(dateTo,'YYYY-M-D');
73
73
 
74
- // d1 と d1 との差分を月単位で得る。その際に小数点以下も取得する。
74
+ // d1 と d2 との差分を月単位で得る。その際に小数点以下も取得する。
75
75
  const monthDiff = d2.diff(d1,'month', true);
76
76
 
77
77
  // 上記で得た monthDiff の整数部分 n と小数部分 r を取得する。

8

テキスト追加

2021/11/27 14:36

投稿

退会済みユーザー
answer CHANGED
@@ -51,4 +51,71 @@
51
51
  あるいは
52
52
  ```javascript
53
53
  const m = Math.ceil(n / 3)
54
- ```
54
+ ```
55
+
56
+ ### 追記2
57
+
58
+ コメントから頂きました、
59
+
60
+ > ・・・得たい結果としては1(か月)+14日(剰余日数)となります。
61
+
62
+ を得るための関数 `monthDiff_md(dateFrom, dateTo)` を作ってみました。
63
+
64
+ > ・・・もっとdayjsでスマートに行けるのであれば、お知恵を頂きたくご返信させていただきました。
65
+
66
+ とのことでしたが、スマートなものになっているかは分かりませんが挙げておきます。
67
+
68
+ ```javascript
69
+ const monthDiff_md = (dateFrom, dateTo) => {
70
+ // 引数で与えられた YYYY-M-D 形式の文字列からdayjsオブジェクトを作る
71
+ const d1 = dayjs(dateFrom, 'YYYY-M-D');
72
+ const d2 = dayjs(dateTo,'YYYY-M-D');
73
+
74
+ // d1 と d1 との差分を月単位で得る。その際に小数点以下も取得する。
75
+ const monthDiff = d2.diff(d1,'month', true);
76
+
77
+ // 上記で得た monthDiff の整数部分 n と小数部分 r を取得する。
78
+ const n = Math.floor(monthDiff);
79
+ const r = monthDiff - n;
80
+
81
+ // d1 に n月 および (n+1)月を加えた日付を作って、d3 および d4 とする。
82
+ const [d3, d4] = [n, n+1].map(x => d1.add(x, 'month'));
83
+
84
+ // d4 と d3 の日数差を計算して m とする。
85
+ const m = d4.diff(d3, 'day');
86
+
87
+ // m に r を乗じた数を作る。この数の単位は日であり理屈上は整数だが、計算結果は整数にごく近い小数になるのでMath.roundする。
88
+ const k = Math.round(m * r)
89
+
90
+ // n と k を返す
91
+ return [n, k];
92
+ }
93
+ ```
94
+ 実行例:
95
+ ```javascript
96
+ const [n, k] = monthDiff_md("2021-6-1","2021-7-15");
97
+
98
+ console.log(n, k);
99
+ ```
100
+ 出力結果:
101
+ > [ 1, 14 ]
102
+
103
+ この`14`日の算出方法を説明します。
104
+
105
+ - dayjsのドキュメントでの[diffの説明](https://day.js.org/docs/en/display/difference) に
106
+
107
+ ```javascript
108
+ const date1 = dayjs('2019-01-25')
109
+ date1.diff('2018-06-05', 'month', true) // 7.645161290322581
110
+ ```
111
+ とあるとおり、diff の第三引数に true を渡すと、小数点以下ありの数値が返ってきます。この小数部分を日数に換算することを考えます。
112
+
113
+ - ご例示の、d1=`"2021-6-1"` と d2=`"2021-7-15"` であれば、`d2.diff(d1,'month', true)` は、私の手元の環境では
114
+ 1.4516129032258065
115
+ という数を返しました。
116
+
117
+ - これの小数部分`r` = 0.4516129032258065 を日数に換算するために、この 0.45・・・に何を掛ければよいかというと、上記のソースコードに出てくる`d3` と `d4` の日数差です。この差は月でいえば一ヶ月ですが、日数換算だと`d3`の月の月末が何日なのかによって変わります。(このへんを任せられるのがdayjsの強みですね)
118
+
119
+ - `d3` と `d4` の日数差を `m` として得て、`m`に先の小数 `r` = 0.45・・・ を乗じると、欲しい剰余日数が出るはずですが、計算結果としては整数にごく近い小数になると思います。私の手元では、
120
+ 14.000000000000002
121
+ となりました。これの小数を Math.round で切り捨てれば、得たい剰余日数の14が得られます。

7

テキスト追加

2021/11/27 14:24

投稿

退会済みユーザー
answer CHANGED
@@ -38,4 +38,17 @@
38
38
  return [n, m];
39
39
  };
40
40
  ```
41
- - ???? [動作確認のサンプル](https://codepen.io/kilesa/pen/ZEJgqgb?editors=0012) @codepen
41
+ - ???? [動作確認のサンプル](https://codepen.io/kilesa/pen/ZEJgqgb?editors=0012) @codepen
42
+
43
+
44
+ ### 追記
45
+
46
+ 上記のコードで、`n` から `m` を得る計算は、以下でもできます。
47
+
48
+ ```javascript
49
+ const m = Math.floor((n + 2) / 3);
50
+ ```
51
+ あるいは
52
+ ```javascript
53
+ const m = Math.ceil(n / 3)
54
+ ```

6

テキスト追加

2021/11/26 23:37

投稿

退会済みユーザー
answer CHANGED
@@ -1,6 +1,6 @@
1
1
  > どなたかアドバイスを頂ければ幸いです。
2
2
 
3
- アドバイスといいますか、自分ならこういのをやるとき、標準のDateではなく[Day.js](https://day.js.org/en/)を使います。たとえば以下ように monthDiff(dateFrom, dateTo) を書けます。
3
+ アドバイスといいますか、自分ならこういった、二つ日付や日時の差分、何らかの単位(月日、時間など)で算出す必要があるとき、標準のDateではなく[Day.js](https://day.js.org/en/)を使います。たとえば、ご質問`monthDiff(dateFrom, dateTo)`以下のように書けます。
4
4
 
5
5
  ```javascript
6
6
  //
@@ -27,7 +27,7 @@
27
27
 
28
28
  - ???? [動作確認のサンプル](https://codepen.io/kilesa/pen/QWMeZWx?editors=0012) @codepen
29
29
 
30
- または、与えられた`YYYY-M-D`形式の文字列の`-D`の部分を削除した文字列を、`dayjs()`に渡して、`YYYY-M`の文字列としてパースしてオブジェクトを作ると、それは指定された月の月初(1日)の日付を表すものになることを利用して、以下のようにも書けます。
30
+ または、与えられた`YYYY-M-D`形式の文字列の`-D`の部分を削除した文字列を、`dayjs()`に渡して、`YYYY-M`の文字列としてパースしてオブジェクトを作ると、指定された月の月初(1日)の日付を表すものになることを利用して、以下のようにも書けます。
31
31
  ```javascript
32
32
  const monthDiff = (dateFrom, dateTo) => {
33
33
  [dateFrom, dateTo] = [dateFrom, dateTo].map(dateStr =>

5

テキスト追加

2021/11/26 23:24

投稿

退会済みユーザー
answer CHANGED
@@ -31,7 +31,7 @@
31
31
  ```javascript
32
32
  const monthDiff = (dateFrom, dateTo) => {
33
33
  [dateFrom, dateTo] = [dateFrom, dateTo].map(dateStr =>
34
- dayjs(dateStr.replace(/-\d{1,2}$/, ''), 'YYYY-M'),
34
+ dayjs(dateStr.replace(/-\d{1,2}$/, ''), 'YYYY-M')
35
35
  );
36
36
  const n = dateTo.diff(dateFrom, 'month') + 1;
37
37
  const m = Math.floor(n / 3) + (n % 3 > 0);

4

テキスト追加

2021/11/26 23:09

投稿

退会済みユーザー
answer CHANGED
@@ -17,11 +17,11 @@
17
17
  const monthDiff = (dateFrom, dateTo) => {
18
18
  const d1 = dayjs(dateFrom, 'YYYY-M-D').startOf('month');
19
19
  const d2 = dayjs(dateTo, 'YYYY-M-D').endOf('month').add(1, 'second');
20
-
20
+
21
21
  const n = d2.diff(d1, 'month');
22
22
  const m = Math.floor(n / 3) + (n % 3 > 0);
23
- return [ n, m ];
23
+ return [n, m];
24
- }
24
+ };
25
25
 
26
26
  ```
27
27
 
@@ -30,12 +30,12 @@
30
30
  または、与えられた`YYYY-M-D`形式の文字列の`-D`の部分を削除した文字列を、`dayjs()`に渡して、`YYYY-M`の文字列としてパースしてオブジェクトを作ると、それは指定された月の月初(1日)の日付を表すものになることを利用して、以下のようにも書けます。
31
31
  ```javascript
32
32
  const monthDiff = (dateFrom, dateTo) => {
33
- [dateFrom, dateTo] = [dateFrom, dateTo].map(
33
+ [dateFrom, dateTo] = [dateFrom, dateTo].map(dateStr =>
34
- dateStr => dayjs(dateStr.replace(/-\d{1,2}$/, ''), 'YYYY-M')
34
+ dayjs(dateStr.replace(/-\d{1,2}$/, ''), 'YYYY-M'),
35
- );
35
+ );
36
36
  const n = dateTo.diff(dateFrom, 'month') + 1;
37
- const m = Math.floor(n / 3) + (n % 3 > 0);
37
+ const m = Math.floor(n / 3) + (n % 3 > 0);
38
- return [ n, m ];
38
+ return [n, m];
39
- }
39
+ };
40
40
  ```
41
41
  - ???? [動作確認のサンプル](https://codepen.io/kilesa/pen/ZEJgqgb?editors=0012) @codepen

3

テキスト追加

2021/11/26 22:55

投稿

退会済みユーザー
answer CHANGED
@@ -1,6 +1,6 @@
1
1
  > どなたかアドバイスを頂ければ幸いです。
2
2
 
3
- 自分ならこういうのやるとき、標準のDateで頑張らいで、迷わず [Day.js](https://day.js.org/en/)を使います。たとえば以下のように monthDiff(dateFrom, dateTo) を作れます。
3
+ アドバイスといいますか、自分ならこういうのやるとき、標準のDateで[Day.js](https://day.js.org/en/)を使います。たとえば以下のように monthDiff(dateFrom, dateTo) を書けます。
4
4
 
5
5
  ```javascript
6
6
  //

2

テキスト追加

2021/11/26 22:32

投稿

退会済みユーザー
answer CHANGED
@@ -27,7 +27,7 @@
27
27
 
28
28
  - ???? [動作確認のサンプル](https://codepen.io/kilesa/pen/QWMeZWx?editors=0012) @codepen
29
29
 
30
- または、与えられた`YYYY-M-D`形式の文字列の`-D`の部分を削除した文字列を、`dayjs()`に渡して、`YYYY-M`の文字列としてパースしてオブジェクトを作ると、それは月初(1日)の日付を表すものになることを利用して、以下のようにも書けます。
30
+ または、与えられた`YYYY-M-D`形式の文字列の`-D`の部分を削除した文字列を、`dayjs()`に渡して、`YYYY-M`の文字列としてパースしてオブジェクトを作ると、それは指定されたの月初(1日)の日付を表すものになることを利用して、以下のようにも書けます。
31
31
  ```javascript
32
32
  const monthDiff = (dateFrom, dateTo) => {
33
33
  [dateFrom, dateTo] = [dateFrom, dateTo].map(

1

テキスト追加

2021/11/26 18:13

投稿

退会済みユーザー
answer CHANGED
@@ -25,4 +25,17 @@
25
25
 
26
26
  ```
27
27
 
28
- - ???? [動作確認のサンプル](https://codepen.io/kilesa/pen/QWMeZWx?editors=0012) @codepen
28
+ - ???? [動作確認のサンプル](https://codepen.io/kilesa/pen/QWMeZWx?editors=0012) @codepen
29
+
30
+ または、与えられた`YYYY-M-D`形式の文字列の`-D`の部分を削除した文字列を、`dayjs()`に渡して、`YYYY-M`の文字列としてパースしてオブジェクトを作ると、それは月初(1日)の日付を表すものになることを利用して、以下のようにも書けます。
31
+ ```javascript
32
+ const monthDiff = (dateFrom, dateTo) => {
33
+ [dateFrom, dateTo] = [dateFrom, dateTo].map(
34
+ dateStr => dayjs(dateStr.replace(/-\d{1,2}$/, ''), 'YYYY-M')
35
+ );
36
+ const n = dateTo.diff(dateFrom, 'month') + 1;
37
+ const m = Math.floor(n / 3) + (n % 3 > 0);
38
+ return [ n, m ];
39
+ }
40
+ ```
41
+ - ???? [動作確認のサンプル](https://codepen.io/kilesa/pen/ZEJgqgb?editors=0012) @codepen