知らなきゃ損!date-fns の Year Helpers で過去の日付を効率的に操作する方法


date-fns ライブラリに搭載されている subYears 関数は、指定された日付から指定された年数分の期間を減算する機能を提供します。具体的には、以下の操作を行います。

  1. 入力された日付を受け取り、内部的に JavaScript の Date オブジェクトに変換します。
  2. 指定された年数分のミリ秒数を計算します。
  3. 計算されたミリ秒数を Date オブジェクトから減算します。
  4. 減算後の新しい日付を Date オブジェクトとして返します。

具体的な使い方

import { subYears } from 'date-fns';

const startDate = new Date(2024, 5, 12); // 2024年6月12日
const subtractedDate = subYears(startDate, 2); // 2022年6月12日

console.log(subtractedDate); // 2022-06-12T00:00:00.000Z

上記コードでは、startDate という変数に 2024年6月12日の日付を代入し、subYears 関数を使用して 2 年前の日付を計算しています。結果として、subtractedDate 変数には 2022年6月12日の日付が格納されます。

オプションパラメータ

subYears 関数は、オプションパラメータとして baseDate を受け取ることができます。baseDate は、減算の基点となる日付を指定します。デフォルトでは、現在の日付が使用されます。

import { subYears } from 'date-fns';

const startDate = new Date(2024, 5, 12);
const baseDate = new Date(2023, 1, 1); // 2023年1月1日
const subtractedDate = subYears(startDate, 2, baseDate); // 2021年1月1日

console.log(subtractedDate); // 2021-01-01T00:00:00.000Z

上記コードでは、baseDate 変数に 2023年1月1日の日付を代入し、subYears 関数を使用して 2023年1月1日からの2年前の日付を計算しています。結果として、subtractedDate 変数には 2021年1月1日の日付が格納されます。

  • 無効な日付や不正なパラメータが渡された場合は、TypeError 例外がスローされます。
  • 閏年を考慮した計算が行われます。
  • subYears 関数は、日付の加減算のみを行うため、時間や分などの情報はそのままで維持されます。
  • date-fns ライブラリは、npm や yarn などのパッケージマネージャーを使用してインストールすることができます。
  • date-fns ライブラリには、addYearssetYear などの Year Helpers 関数が用意されています。これらの関数は、それぞれ異なる操作を行うため、用途に合わせて使い分けることができます。


特定の年の1月1日を計算

import { subYears, startOfYear } from 'date-fns';

const targetYear = 2020;
const targetDate = subYears(startOfYear(new Date()), targetYear - 2024);

console.log(targetDate); // 2020-01-01T00:00:00.000Z

このコードでは、targetYear 変数に 2020 という値を代入し、subYears 関数と startOfYear 関数を使用して、2020年の1月1日の日付を計算しています。

特定の月の最終日を計算

import { subYears, lastDayOfMonth } from 'date-fns';

const targetYear = 2022;
const targetMonth = 12; // 12 = 12月
const targetDate = subYears(lastDayOfMonth(new Date(targetYear, targetMonth - 1)), 1);

console.log(targetDate); // 2021-12-31T00:00:00.000Z

このコードでは、targetYear 変数に 2022 という値を代入し、targetMonth 変数に 12 (12月は12番目の月) という値を代入し、subYears 関数と lastDayOfMonth 関数を使用して、2022年12月31日の日付を計算しています。

import { subYears, getDay } from 'date-fns';

const targetDay = 3; // 3 = 火曜日
const targetDate = subYears(new Date(), 1);
const desiredDate = subYears(targetDate, getDay(targetDate) - targetDay);

console.log(desiredDate); // 2023-06-06T00:00:00.000Z


以下に、subYears 関数の代替方法として考えられる選択肢をいくつかご紹介します。

JavaScript の組み込み関数を使用する

JavaScript には、日付を操作するための組み込み関数がいくつか用意されています。例えば、以下のコードは subYears 関数と同等の処理を setDate 関数を使用して実現しています。

const startDate = new Date(2024, 5, 12);
const subtractedDate = new Date(startDate.setDate(startDate.getDate() - 365 * 2));

console.log(subtractedDate); // 2022-06-12T00:00:00.000Z

上記コードでは、startDate オブジェクトから 2 年前の日付を計算するために、setDate メソッドを使用して startDate オブジェクトの日付を 2 年分減算しています。

Moment.js などのライブラリを使用する

date-fns ライブラリ以外にも、Moment.js などの日付操作ライブラリは数多く存在します。これらのライブラリは、date-fns ライブラリにはない機能を提供している場合もあるため、状況に合わせて使い分けることができます。

Moment.js で subYears 関数と同等の処理を行う場合は、以下のコードのように subtract メソッドを使用することができます。

const moment = require('moment');

const startDate = moment('2024-06-12');
const subtractedDate = startDate.subtract(2, 'years');

console.log(subtractedDate.format('YYYY-MM-DD')); // 2022-06-12

カスタムロジックを実装する

上記の方法で解決できない場合は、カスタムロジックを実装する方法も考えられます。例えば、以下のように for ループを使用して 1 日ずつ減算していく方法があります。

const startDate = new Date(2024, 5, 12);
const subtractedDate = new Date(startDate);

for (let i = 0; i < 365 * 2; i++) {
  subtractedDate.setDate(subtractedDate.getDate() - 1);
}

console.log(subtractedDate); // 2022-06-12T00:00:00.000Z

最適な方法の選択

どの方法が最適かは、状況によって異なります。以下の点を考慮して選択してください。

  • パフォーマンス: 処理速度が重要な場合は、カスタムロジックを実装する方が効率的な場合があります。
  • 機能: より多くの機能が必要な場合は、Moment.js などのライブラリを使用する方が良いかもしれません。
  • シンプルさ: コードのシンプルさを重視する場合は、JavaScript の組み込み関数を使用するのがおすすめです。
  • 上記以外にも、subYears 関数の代替方法として考えられる方法はいくつか存在します。