日付と時刻——TODAY/DATE/DATEDIF/EDATE と日付計算
レッスン5:日付と時刻——TODAY/DATE/DATEDIF/EDATE と日付計算
このレッスンで学ぶこと
- 日付の正体(シリアル値)を理解する
- TODAY・NOW で「今日」「今」を取得する使い方を持つ
- DATE・YEAR・MONTH・DAY で日付を構成・分解できる
- DATEDIF で 2 つの日付の差を計算できる
- EDATE で n か月後を計算する発想を持つ
- WORKDAY・NETWORKDAYS で営業日を扱える
- WEEKDAY・TEXT で曜日を扱える
- よくある日付トラブル(書式違い・テキストの日付)の対処を整理する
前のレッスンでは、データ整形の関数(TEXT・TRIM・LEFT/RIGHT/MID・結合・SUBSTITUTE)を扱いました。今回のレッスンでは、業務で必ず出会う「日付」を扱います。日付の計算は、見た目は単純ですが、内部の仕組みを知らないと事故が多発します。本レッスンで、日付の正体と扱い方を整理します。
日付の正体——シリアル値
Excel/Google スプレッドシートでは、日付は内部的に「シリアル値(serial value)」という整数で扱われています。
シリアル値の仕組み
- 1900 年 1 月 1 日を「1」とする
- 1 日進むごとに「1」を足す
- 例:2026 年 6 月 18 日は「46190」(1900/1/1 から 46190 日目)
セルに「2026/6/18」と表示されていても、内部の値は「46190」という数値です。Excel が表示形式を「日付」に設定して、人間にわかる形に見せているだけです。
シリアル値を確認する
セルの表示形式を「数値」または「標準」に変えると、日付がシリアル値(数値)として見えます。
なぜシリアル値なのか
シリアル値で扱う理由は、日付の計算を簡単にするためです。
- 「2 つの日付の差は何日か」→ 引き算するだけ
- 「10 日後はいつか」→ 足し算するだけ
- 「3 か月後はいつか」→ EDATE 関数で処理
- 「平日か休日か」→ 7 で割った余りで判定
シリアル値を意識すると、「日付計算の不思議」が「数値計算」に置き換わります。
時刻はシリアル値の小数部分
時刻は、シリアル値の小数部分で表現されます。
- 0.0 = 0:00(午前 0 時)
- 0.5 = 12:00(正午)
- 0.75 = 18:00(午後 6 時)
「2026/6/18 12:00」は「46190.5」というシリアル値です。
💡 ポイント 日付の表示が崩れたとき、内部のシリアル値を確認すると原因がわかります。「テキストとして入力された日付」は数値ではなく文字列で、シリアル値を持ちません。
TODAY・NOW——「今日」「今」を取得する
TODAY——今日の日付
=TODAY()
… 結果:そのファイルを開いた日(または再計算された日)
引数はありません。シートを開き直すたびに、その日に更新されます。
NOW——今の日時
=NOW()
… 結果:そのファイルを開いた日時
時刻まで含めて返します。
よくある使い方
- 月次レポートのタイトルに「2026/06/18 時点」と自動表示
- 「最終更新日:」の自動表示
- 経過日数の計算:
=TODAY() - 契約開始日
注意点
TODAY と NOW は「ファイルを開いた日時」で更新されるため、「特定の日時を固定したい」場合は値として書き込みます(コピー → 値貼り付け)。
⚠️ 注意 帳票や契約書のように「特定日時で固定したい」場合は、TODAY を使ったままにせず、シート完成時に値貼り付けで固定するのが鉄則です。
DATE・YEAR・MONTH・DAY——日付の構成と分解
DATE——年・月・日から日付を構成
=DATE(年, 月, 日)
=DATE(2026, 6, 18)
… 結果:2026/6/18
年・月・日を別々のセルから組み立てる場面で便利です。
=DATE(A1, B1, C1)
… A1 が年、B1 が月、C1 が日のとき、日付を構成
YEAR・MONTH・DAY——日付から要素を取り出す
=YEAR(A1)
… A1 の年を取得(例:2026)
=MONTH(A1)
… A1 の月を取得(例:6)
=DAY(A1)
… A1 の日を取得(例:18)
「日付列から月だけ抽出して、月別に集計する」場面で便利です。
月初・月末の計算
=DATE(YEAR(A1), MONTH(A1), 1)
… A1 と同じ月の 1 日
=DATE(YEAR(A1), MONTH(A1) + 1, 0)
… A1 と同じ月の末日(翌月 0 日 = その月の末日)
=EOMONTH(A1, 0)
… A1 と同じ月の末日(EOMONTH 関数で直接取得)
=EOMONTH(A1, 1)
… A1 の翌月の末日
📝 補足 月末の計算は「翌月 0 日」のトリックでも可能ですが、EOMONTH のほうが意図が明確です。EOMONTH は Microsoft 365 でも古い Excel でも使えます。
DATEDIF——2 つの日付の差
DATEDIF(Date + Difference)は、2 つの日付の差を年・月・日の単位で計算します。
=DATEDIF(開始日, 終了日, "単位")
単位の種類:
| 単位 | 意味 |
|---|---|
"Y" |
完全な年数 |
"M" |
完全な月数 |
"D" |
日数 |
"MD" |
月日を無視した日数 |
"YM" |
年を無視した月数 |
"YD" |
年を無視した日数 |
例:
=DATEDIF("2020/4/1", "2026/6/18", "Y")
… 結果:6(完全な 6 年)
=DATEDIF("2020/4/1", "2026/6/18", "M")
… 結果:74(完全な 74 か月)
=DATEDIF("2020/4/1", "2026/6/18", "D")
… 結果:2269(2269 日)
業務でよく使うのは「Y」(年齢、勤続年数)です。
「年齢」の計算
=DATEDIF(生年月日, TODAY(), "Y")
… 今日時点の満年齢
「勤続年数と月数」を組み合わせる
=DATEDIF(入社日, TODAY(), "Y") & "年" & DATEDIF(入社日, TODAY(), "YM") & "か月"
… 結果:例「6年2か月」
DATEDIF の注意点
DATEDIF はかなり古い関数で、Excel の関数一覧に表示されません。手で入力する必要があります。また、Google スプレッドシートでも使えますが、互換性確認は行ってください。
💡 ポイント 年齢・勤続年数の計算は DATEDIF が最もシンプルです。引き算で何日になるか計算してから 365 で割るのは、うるう年で誤差が出るので避けます。
EDATE——n か月後・前
EDATE は、ある日付の「n か月後」または「n か月前」を計算します。
=EDATE(開始日, 月数)
例:
=EDATE("2026/6/18", 3)
… 結果:2026/9/18(3 か月後)
=EDATE("2026/6/18", -3)
… 結果:2026/3/18(3 か月前)
=EDATE("2026/1/31", 1)
… 結果:2026/2/28(月末調整あり)
よくある使い方
- 契約満了日:
=EDATE(契約開始日, 契約月数) - 6 か月後の更新日:
=EDATE(TODAY(), 6) - 1 年前の同月:
=EDATE(TODAY(), -12)
EOMONTH との違い
- EDATE:n か月後の「同じ日」を返す
- EOMONTH:n か月後の「月末」を返す
両者を使い分けます。
WORKDAY・NETWORKDAYS——営業日の計算
営業日(土日祝を除いた日)を扱う関数も用意されています。
WORKDAY——n 営業日後
=WORKDAY(開始日, 営業日数, [祝日範囲])
例:
=WORKDAY("2026/6/18", 5)
… 結果:2026/6/25(5 営業日後、ただし祝日は考慮していない)
=WORKDAY("2026/6/18", 5, 祝日リスト範囲)
… 5 営業日後、祝日リストを除外
「5 営業日後の納期」「3 営業日後の支払日」のような計算に使います。
NETWORKDAYS——営業日数を計算
=NETWORKDAYS(開始日, 終了日, [祝日範囲])
例:
=NETWORKDAYS("2026/6/1", "2026/6/30", 祝日リスト範囲)
… 6 月の営業日数(土日を除いて、さらに祝日を除いた日数)
「月の営業日数」「2 つの日付の間の営業日数」を計算します。
祝日リストを別シートに置く
WORKDAY と NETWORKDAYS の祝日範囲には、祝日を縦に並べたセル範囲を渡します。
(祝日シート)
| 祝日 |
| 2026/1/1 |
| 2026/1/12 |
| 2026/2/11 |
… (以下、年内の祝日)
別シートに祝日リストを作って、毎年更新する運用が一般的です。
📝 補足 WORKDAY.INTL と NETWORKDAYS.INTL という関数もあり、土日以外の休日設定(例:木曜と金曜が休みなど)に対応できます。海外取引で使う場面があります。
WEEKDAY・TEXT——曜日を扱う
WEEKDAY——曜日の番号を取得
=WEEKDAY(日付, [種類])
種類が 1 または省略:日曜 = 1、月曜 = 2、……土曜 = 7
種類が 2:月曜 = 1、火曜 = 2、……日曜 = 7
例:
=WEEKDAY("2026/6/18")
… 結果:5(2026/6/18 は木曜日、日曜起算で 5 番目)
TEXT で曜日を文字列に
WEEKDAY で番号を取得するより、TEXT で直接「木」「木曜日」のような文字列を出すほうがわかりやすいです。
=TEXT(A1, "aaa")
… 結果:「木」
=TEXT(A1, "aaaa")
… 結果:「木曜日」
平日判定
=IF(WEEKDAY(A1, 2) <= 5, "平日", "休日")
… WEEKDAY を 2(月曜起算)で取得し、5 以下なら平日
よくある日付トラブル
業務で出会う日付のトラブルを 3 つ紹介します。
トラブル 1:日付なのに集計できない
「2026/6/18」と表示されているのに、SUMIF や VLOOKUP の検索値に使うと #N/A が出る。原因は、セルの値が「日付」ではなく「文字列」になっていることです。
確認方法:
- セルの表示形式を「標準」に変えてシリアル値が出ればOK、文字列のままなら NG
=ISNUMBER(A1)で TRUE なら数値(日付)、FALSE なら文字列
対処:
=DATEVALUE(A1)
… 文字列を日付(シリアル値)に変換
ただし、文字列の書式が Excel の認識できる形(「2026/6/18」「2026-06-18」など)でないと変換できません。
トラブル 2:書式違いで検索エラー
VLOOKUP の検索値が「2026/6/18」、検索範囲の値が「2026-06-18」だと、見つかりません。表示は同じでも、内部の値(または書式)が違うと別物扱いです。
対処:
- TEXT 関数で両方を同じ書式に揃える
- DATEVALUE で文字列を日付に変換し、同じシリアル値にする
トラブル 3:30 日後の計算がズレる
「30 日後」で =A1+30 を計算したら、想定していた日付と違う日になる。これは Excel の不具合ではなく、「30 日後 ≠ 1 か月後」という現実です。
例えば、「2026/1/31 の 30 日後」は「2026/3/2」です。1 月から 2 月をまたぐと、30 日では足りないからです。
「1 か月後」を求めるなら、=A1+30 ではなく =EDATE(A1, 1) を使います。
⚠️ 注意 「30 日後」と「1 か月後」の取り違えは、契約管理・サブスクリプション業務で繰り返し起きるバグの原因です。意味で関数を選びましょう。
講師の現場メモ:「契約満了日の計算ミスで違約金請求」
私(水田)が大手コンサルファーム時代に支援した、ある中堅サービス業の話です。サブスクリプション契約管理シートで、契約満了日を =契約開始日 + 365 で計算していました。
「1 年契約なら 365 日後でいいだろう」という理屈です。一見すると問題なさそうですが、
- うるう年(2024 年など)の影響で 1 日ズレる
- 30 日締めの月、31 日締めの月で月初がズレる
- 顧客が「自分の契約は X 月 Y 日から 1 年」と認識している日付と合わない
結果、ある月、契約満了日が顧客の認識と 1 日ズレて、顧客から「契約期間外なのにサービスが止まった」と違約金請求が来ました。少額でしたが、信頼を損ねる事故になりました。
私はその会社のシートを、=EDATE(契約開始日, 契約月数) に書き換えました。これで「契約開始日と同じ日付の n か月後」が確実に取得できます。さらに、
- 契約期間を「12 か月」で持つ(「365 日」ではなく)
- 満了日を EDATE で計算
- 検算式(顧客と認識が合うか)を月次でチェック
- 過去 5 年の契約を遡って整合性確認
を行いました。整合性確認で過去契約 7 件で 1 日ズレが見つかり、すべて顧客にお詫びと精算を行いました。
このときに痛感したのは、日付の関数は「意味」で選ぶことが重要だ、ということです。「1 年後」を求めているのに +365 を使うと、うるう年やサブスクリプションの月締めでズレが必ず出ます。EDATE は名前は地味ですが、契約期間を「月単位で扱う」業務の中核関数です。
本コースで日付の関数を 1 レッスン分扱うのは、こうした事故を皆さんの業務で起こさないためです。日付は単純そうで、実は最も事故の多い領域です。
まとめ
このレッスンでは、以下のことを学びました。
- 日付の正体はシリアル値(1900/1/1 を 1 として、日数を整数で表現)
- 時刻はシリアル値の小数部分(0.5 = 12:00)
- TODAY():今日の日付、NOW():今の日時。引数なし、再計算で更新
- 固定したい日時は値貼り付けで確定する
- DATE で年・月・日から日付を構成、YEAR/MONTH/DAY で分解
- EOMONTH で月末を直接取得
- DATEDIF:2 つの日付の差を Y/M/D 単位で計算。年齢・勤続年数で活躍。関数一覧に出ないので手入力
- EDATE:n か月後・前を計算。契約満了日・更新日に
- WORKDAY:n 営業日後、NETWORKDAYS:営業日数。祝日リストを別シートで管理
- WEEKDAY と TEXT で曜日を扱う。TEXT(A1, "aaa") で「木」が直接得られる
- トラブル:文字列の日付(DATEVALUE で変換)、書式違い(TEXT または DATEVALUE で揃える)、30 日後と 1 か月後の取り違え(EDATE を使う)
- 日付の関数は「意味」で選ぶ。「1 年後」なら
+365ではなく=EDATE(A1, 12)を選ぶ
次のレッスンでは、集計とピボットテーブルを扱います。大量データを 1 分で要約する発想を持ち帰ります。
確認クイズ
このレッスンの理解度をチェックしましょう。