真の「日付のみ」のデータ型がないのはなぜですか?


24

本当に「たった1日」のデータセットにDateTime値を使用しなければならないことに、とてつもなくイライラしています。誕生日は最も一般的な例ですが、これは常にビジネスアプリケーションで発生します。

「日付のみ」のレコードの「時刻」部分を「正午」に設定することに慣れてきました(タイムゾーンに関係なく日付が変更されることを回避します)。これはハックのように思え、私はこの問題を巡るジュニア開発者からのバグを永遠に見つけています。

時間は常に固定小数点に対して相対的です。午後4時は、子午線または正午の4時間後です。移動中の太陽の最高点は観測可能であり、座標系を設定できます。正午の3時間前(前子午線)、正午の2時間後、1970年1月1日から1441899402938ミリ秒。デカルト世界で育った人々にとって、これは2番目の性質です。

ただし、カレンダーはデカルトより前のものです。私の主張は、モジュロ関数が適用される列挙としてより適切に考えられているということです。月曜日が日曜日に続き、日曜日が土曜日に続くという事実がわかるまで続きます。正負はありません。モジュラスまたは絶対値です。

同様に年が繰り返されます。誕生日、記念日、子供の誕生日など、365日ごと(またはそれ以降)に特別な日がいくつかあります。ビジネススケジューリングアプリケーションには、7日ごと、月の最初の火曜日などの会議の例がたくさんあります。これを浮動小数点数にマッピングすることができます。実際には、これを上記の数にマッピングすることで、従来の方法では非常に困難だった多くの問題を解決できますが、それが唯一の方法ではありません。

DateTimesを使用してDatesを保存するという「丸い穴の四角い釘」の性質に対する認識と理解は、私の意見では優れたプログラマーになります。

Dateクラスを定義する際にスケジューリングアプリケーションとして明示的に意図されたアプリケーションに価値はありますか、それとも「正午にすべての時間を設定する」ことが最善のアプローチですか。DateTimeを使用し、Timeコンポーネントを正午に設定すると、どのような問題が発生する可能性がありますか?そのようなアプローチでタイムゾーンのシフトを考慮することができますか?私はMomentJSを使用しましたが、それはちょうど良いDateクラスだと思います。


7
これは非常に興味深い質問です。誕生日の例を考えてみましょう。それは人間にしか意味がありません。私は1か所に住んでいて、誰もが同じように目覚めます。数学的に表現する必要があるとすぐに、非常に複雑になります。作業シフトの開始/終了時間などのように、彼らは「あなたが作業しているタイムゾーンでの一日の時間のある「時間」をアレントものと同じ
ユアン・

3
NodaTime(Date&TimeのC#ライブラリ)には、日付のタイプがあります。
CodesInChaos

5
時刻をUTCで保存し、日付の問題やタイムゾーンの問題はありません。
ローレンペクテル

3
「しかし、これはハッキングのように思えます。私はこの問題を巡るジュニア開発者のバグを永遠に見つけています。」-独自のDateOnlyクラスなどを作成して、それを1日と呼ばないのはなぜですか。
ブランディン

5
@MichaelBlackburn私は本気です。あなたの説明は、ビジネスルールを強制する独自のデータタイプの状況に正確に聞こえます(日付のみ、たとえば、正午に設定された時間部分で「DateTime」として内部的に保存できます)、その後、必要な部分のみを公開します(月、日など年/年なし)。
ブランディン

回答:


15

:まず第一に、の方法のうち一つを取得してみましょう誕生日には、一つのことをしている-の出生日付は別です。A 誕生日には、それは時間、分などの構成要素ではないだけを欠いているが、それはまた、年間の部品がないため、エキゾチックなデータ型です。誕生日に本当に対処したい場合は、月番号と日番号のみを含み、組み込みの日時データ型のいずれにも関連しない独自のデータ型を作成することをお勧めします。

一方、もしあなたが生年を追跡したいなら、あなたが持っているのは誕生日ではなく、生年月日です。したがって、問題はなぜ日付のみのデータ型がないのかということになるので、生年月日を便利に表すことができ、代わりに人気のある言語は時間コンポーネントも含む何らかのタイプを使用するように強制するようです。

すべてのプログラミング言語が時間コンポーネントを含む一時データ型のみを提供するというのは真実ではないことを簡単に言及させてください。RDBMSとそれに対応するSQLダイアレクトで日付のみのデータ型に遭遇しました。しかし、それは関係ありません。これらのデータ型が存在するという事実は、それらが良いものであることを意味するものではなく、RDBMSはストレージと表現を混同する長い歴史を持っています。

時間を調整していることに気付いた瞬間に、このような日付のみのデータ型を使用することが悪い考えである理由を理解できます。ほとんどの人は時間が何であるかの非常に漠然とした考えを持っており、このアイデアは、これらの概念は、排他的であることを実現することなく、そのような年、月と日のように難解な文化的な概念が含まれて表現:彼らは人間に時間を表すためにのみ有用であり、受信します人間からの入力としての時間。実際の時間入力GUIコントロールの下の任意のレイヤーで、時間は時間座標として表されるべきであり、通常は、ある起源からの時間単位の単一の数です。

たとえばDateTime、Microsoft Dotnetのデータ型では、時間単位は100ナノ秒であり、時間の起点は0001 CEの1月1日午前0時です。

不可解な排他的表現のもう1つの例は、度、度の分、度の秒を使用した角度測定です。もちろん、有用な計算を行うには、内部でラジアンを使用する必要があります。必要に応じて、人間のユーザーとやり取りするときに度に変換したり、度から変換したりします。

そのため、人間が読める形式の測定値と実際の測定値を混同しないでください。多くの場合、測定の性質に最も近い測定を実現するための理想的な方法は、その測定の人間が読み取れる表現とは非常に異なります。

これらすべてに照らして、日付のみを表す時間データ型の要求は、度数のみを表現できる角度データ型の要求に似ており、それ以上の精度を明示的に妨げます。このようなデータ型は非常に制限され、最終的には役に立たなくなります。何とか便利なことをするためには、とにかくラジアンとの間で変換する必要があるからです。

生年月日の問題は、不正確な時間座標があることです。もちろん、その人は特定の瞬間に生まれましたが、時間と分は病院によって記録されていないか、私たちはそうしていませんそれらを気にします。したがって、実際に起こっているのは、生年月日と時間の座標に誤差、許容範囲、または不確実性がある場合、それをそのように扱うのが最善であるということです。そして、暗黙の+12 -12時間の不確実性を考慮します。それがまさにあなたが直観的に到達した解決策です。


4
これは、Timeよりも古い概念である「Days」には当てはまりません。それらは、最も適切に列挙またはモジュラスと考えられています。日曜日は月曜日に続き、土曜日に続く日曜日に戻るまで続きます。それは本当に違うものです。
マイケルブラックバーン

10
まあ、もちろん、ほとんどの病院では標準的な慣行だ-病院は出産の時間を書き留めました。それはまったく問題ではありません。問題は、イベント(誕生日、祝日、記念日など)を記念するために、1日よりも細かい解決策を使用しないか、解決したくないということです。誕生日が来たときに最初に会う人に聞いてみてください。1か月と1日に渡されますが、1時間と1分は渡されません。また、常にスケールを含む単位を使用します:ミリメートル、キログラム、メガワット、そして実際、マイクロファラッド。
カレブ

4
-1:時間のすべての使用が時間の単一の瞬間を表すことではありません。誕生日は別のアイデアであり、グレゴリオ暦の月と日で表されます。「今日はケビンの誕生日ですか」と尋ねるのは理にかなっています。答えは場所に依存します。私がシドニーにいる場合は私の誕生日かもしれませんが、代わりにホノルルにいた場合は、まだ数時間はありません。
ケビンクライン

6
@MikeNakis結果は、ナンセンスではなく、マイクロアンペアになります。さらに重要なのは、秒またはミリ秒ではなく日付を使用する場合、通常は特定の時間ではなく、1日全体、つまり期間について話していることです。コンテキストによっては、繰り返しイベントになる場合があります。
カレブ

4
OPは誕生日について話していましたが、誕生日は正確にはjava.util.MonthDayで表されます。誕生日は測定値ではなく、毎年繰り返される人間の概念です。単一の時点で表されていない時間の人間の考えがたくさんあります。
ケビンクライン

9

日付と時刻はコンテキストに応じて多くの異なるものであり、すべてのユースケースをカバーするために多くの別個のタイプが必要です。

DateTime多くの言語で型存在時間に正確な時点(「瞬時」)を表します。これを超えて、多くの場合あいまいでコンテキストに依存する、暦日、繰り返し日付、月、年などの多くの相対的または「人間」の時間とタイムスパンの概念があります。これらのタイプは普遍的に有用ではありませんが、カレンダー、スケジューリングツール、時間の人間の概念と相互作用する他のアプリケーションなどの特定のアプリケーションドメインで必要です。

カレンダーアプリのようなものを書いている場合、Joda-timeのような豊富な時間タイプのセットを提供するライブラリを使用することで間違いなくメリットがあります。たとえばLocalDate、時間のない日付。これはDateTime、時間部分がゼロに設定された通常とは異なるセマンティクスを持ちます。これはDateTime、特定の時点(特定のタイムゾーンの午前0時)をLocalDate示しながら、1日全体を示し、特定のタイムゾーンに関連付けられていないためです。これは、一方を他方に直接翻訳できないことも意味します。

LocalDateDateTimeタイムゾーンを考慮する必要がないためよりも確かに単純ですが、他の問題に注意する必要があります。たとえば、タイムゾーンを通過するときに現在の日付が実際に逆行する可能性があり、同じ瞬間が異なるタイムゾーンの異なる日付に対応しています。ネットワークアプリまたはWebアプリでローカル日付を使用している場合、これらの問題に十分注意する必要があります。日付から時刻部分を削除しても、タイムゾーンの根本的な問題は解決しません!また、歴史的な日付と異なる文化を考慮すると、同じ日付が、ユリウス暦とグレゴリオ暦の時間の大幅に異なるインスタンスに対応する可能性があるため、さらに複雑になります。

ここで、言語にLocalDate 組み込みのようなものがない理由を尋ねます。まず最初に、SQLやVisual Basicなどの一部の言語には、時刻部分のない日付型があります。また、JavaもLocalDate最近のバージョンに追加しました。しかし、.Netのような他のプラットフォームにはありません。これが標準ライブラリに含まれていない理由に本当に答えることができるのは言語設計者だけですが、「インスタント時間」は概念的にシンプルで普遍的に便利ですが、他の時間概念は特定のアプリケーションドメイン(カレンダーなど) 。)。そのため、アプリケーション開発者に、より複雑なユースケースを処理するカスタムタイプを記述させたり、(Joda-timeのような)サードパーティライブラリによって処理させたりするのは理にかなっています。


5

本当に「たった1日」のデータセットにDateTime値を使用しなければならないことに、とてつもなくイライラしています。誕生日は最も一般的な例ですが、これは常にビジネスアプリケーションで発生します。

これはおそらく、カレンダーが複雑であり、非常に多くの異なる方法で使用されているため、多くの分野で役立つほど単純で一般的なクラスを誰も理解できなかったためです。

プログラミング言語で一般的に見られる日付タイプは、コンピューターシステム内のトランザクションを正確に日付付けするために使用できます。他のユースケースでは、カスタムライブラリが必要になる可能性があります。

カレンダーに関する事実の短いリストは、その複雑さを示しています。それらのほとんどは歴史的なものであるため、1.1.1970以降の日付に注意を制限している場合、この影響を受けません。ただし、アプリケーションが19世紀後半より前の日付で動作する必要がある場合は、これらの事実が重要になります。可能なユースケースは、あらゆる種類の履歴データベース(書籍、系図)だけでなく、現在も活動を続けている大企業または組織の資産です。

これらすべての事実は、Julien Signollesによって書かれたOCamlのカレンダーライブラリにある優れたFAQから引用されています。

  1. ユリウス暦は、紀元前45年にジュリアスシーザーによって導入されました。各国がグレゴリオ暦に変更し始めた1500年代まで、一般的に使用されていました(セクション2.2)。ただし、一部の国(ギリシャやロシアなど)は1900年代にそれを使用し、ロシアの正教会では、他の正教会でも同様に使用されています。

  2. ユリウス暦からグレゴリオ暦への切り替えは一様に行われず、変更の年によっては10〜13日が削除されました。たとえば、フランスでは1582年12月9日の後に1582年12月20日が続き、ギリシャでは1924年3月9日の後に1924年3月23日が続きました。

  3. 現代でも、いくつかの暦を引用するために多くの異なるカレンダー(グレゴリオ暦、正統派、イスラム、中国語)が使用されています。

ここで、一般的なビジネスオペレーションに役立つオペレーションがバンドルされた日付タイプを希望します。私は一般的な事業運営のようなものはないと思います。たとえば、金融の世界では、以下を計算する必要があります。

  1. 年の端数(「6か月」などは「0.5」に対応します)は、特定の期間のローンの実際の利息を計算するために金利と組み合わせて使用​​されます。これらの端数を計算するための6〜10のレシピがあり、それぞれがうるう年の長さ、2月の最後の日に対する期間の位置、および月の期間を処理する方法が異なります。

  2. 日付のローリングでは、記念日を計算するときに、ビジネスカレンダーとルール(6つ以上の異なるルールのセットから選択)を使用して、記念日を休日から営業日にシフトします。

金融業界で働く人々にとって、これらのすべての機能とルールを実装していないカレンダータイプは役に立たない。他の多くの業界では、カレンダーでのカスタム計算を必要とする他のタイプの習慣や慣習がある可能性があります。

Dateクラスを定義する際にスケジューリングアプリケーションとして明示的に意図されたアプリケーションに価値はありますか、それとも「正午にすべての時間を設定する」ことが最善のアプローチですか。DateTimeを使用し、Timeコンポーネントを正午に設定すると、どのような問題が発生する可能性がありますか?そのようなアプローチでタイムゾーンのシフトを考慮することができますか?私はMomentJSを使用しましたが、それはちょうど良いDateクラスだと思います。

単一の暦日を追跡する必要がある場合、おそらく、その暦日のユリウス日を表す大きな整数を使用するのが最善の方法です。ユリウス日から暦日に変換するアルゴリズム(年、月、カレンダーで説明)は広く知られており、完全にテストされているため、アプリケーションに簡単に実装できます。 2月29日に発生するイベントの記念日を計算するケース。


2

上記の答えのマイク・ナキスは、一般に時間は絶対的な測定座標であり、他の通信、その時間座標の想定される状態または永続性は、単に時間座標の抽象表現であると説明するよりも良い仕事をしていると思います。

曜日を実際の時点の単なるある種の表現と呼ぶとき、あなたはそのような表現に話します。実際には、それよりもやや複雑です。特定の時点で曜日を返す関数を作成するように依頼された場合、そのようなアルゴリズムへの入力として必要になる次の情報を考慮してください。時刻、カレンダー、考慮するタイムゾーンが必要になります(タイムゾーンは常に変更されるため、その有効なタイムゾーンがいつ特定の時間座標で終了するかを知る必要があります。北朝鮮最近たとえば、彼らの時間を変更しました!)、そして夏時間が有効な場合、これも時間とともに変化します。次に、ローカルタイムゾーンでDateTimeが与えられたかどうかを検討します。

この一見単純な質問がどれほど複雑になるかを見ることができます。

経験の浅い開発者によって作成された製品の訪問スケジュールアプリケーションのすべてのバグを修正したことがある時点で、私があなたの靴で感じていた痛みを知っています。すべてを廃棄する必要がありました。

時間は確かに調整されますが、単なる日付に加えて、次のように必要になる可能性のある他の時間依存データを検討してください。

期間:特定の時間座標が指定されていない時間の長さまたは経過を示すミリ秒のスパン。ユースケースは、

ユーザーとして、私はこのタスクが隔週の水曜日の深夜ジョブの完了後15秒で実行されることを望みます。

間隔: 2つの特定の時間座標間の時間範囲。間隔を考慮したいユースケース。

ユーザーとして、指定された期間内に完全に含まれるすべての月の日を確認する必要があります。

もう1つの簡単なポイントは、時間ベースのデータの浮動小数点数についてコメントをしたことです。浮動小数点演算は、必然的に丸め誤差につながり、時間の必要に応じて正確な測定値が得られない場合があります。

結論として、この情報はすべて、必然的に次の設計上の考慮事項につながります。

  • 特定の時点または範囲は、必要に応じてUTCに簡単に抽象化できるように、UTCまたは十分な情報を含むデータ型で保持する必要があります。
  • アプリケーションロジックは、UTCまたはUTC座標の範囲を、エンドユーザーにとってより消化しやすい表現データ状態にフォーマットするように作成する必要があります。
  • 重要な期間はミリ秒単位で維持する必要があります
  • 時間に関するデータの表示に関するロケール固有またはエンドユーザーの設定は、追加データとして保持し、表示オプションのように扱う必要があります。(例:キオスクA、中央時間帯、軍事時間形式、またはユーザーBの設定、テルアビブの標準時間(GMT + 7:00)時間帯など)
  • FP番号を避ける

1
これはどれも「不可避」ではありません。多くのアプリケーションで一般的ですが、Large Hadron Colliderはナノ秒スケールのイベントを処理します。ミリ秒には十分な精度がないため、システム時間はマイクロ秒に移動しました。カレンダーアプリには、イベントを作成したのと同じタイムゾーンにいるかどうかに関係なく、ローカルのカレンダー日に発生する日付の概念が必要です。
アランシュトコ

1
@AlanShutkoそして、必要な「追加データ」は、ローカルタイムゾーン、日数、およびキャプチャする必要があるその他の重要なデータなどです。ただし、特定の時点がアルゴリズムにとって重要ではない場合でも、これらはすべて単一の時点に対する単なる抽象化です。ナノ秒、さらにはマイクロ秒のスケールに関しては、私の答えはWebおよびLOBタイプのソフトウェアを対象としています。選択するLHC言語はC#またはJavascriptであるとは思いません。
maple_shaft

1
ミリ秒は、反復可能な物理プロセスに最適です。人間活動の場合、適切な単位は公称日数である場合があります。たとえば、1日の終わりに出荷された場合、3日後に目的地で使用できるようになります。
ケビンクライン

過去には、時間座標に64ビット浮動小数点数を使用することを検討していましたが、より重要なのは時間範囲に使用することです。 。(だから、恐竜が6500万年前に死んだとしたら、数年を与えたり、取ったりしますか?)それで、なぜ彼らは避けるべきだと言うのですか?
マイクナキス

マイク、私は、10進数から2進数の値に変換するため、FP数学が必然的に丸められることに関心があると思います。たとえば、0.3は2進のFP数として表される場合、繰り返し10進数であるため、正確に表すことはできません。容量が不足しているわけではありませんが、精度が不足しています。
マイケルブラックバーン

2

要するに、ほとんどのコンピューターベースの時間タイプは、時間とタイムゾーンの問題を適切に処理することに焦点を合わせているためです。

通常のアプローチではうまく機能しない2つのエッジケースがあります。現地時間を使用して夏時間の変更の反対側にある時点を設定すると、下位の抽象化レイヤーによってUTCに変換され、会議の1時間早く/遅くなります。

もう1つは、(質問によると)人の生年月日を記録するなど、任意の日付情報をモデル化することです。ニュージーランドとハワイの2人が同時に生まれた場合を想像してください。可能性としては、パスポートに異なる生年月日があり、ハワイで生まれた人がニュージーランドに移住した場合、まったく同じ時間住んでいたにもかかわらず、ニュージーランド生まれの人よりも1日古いと見なされます。

日付を正午の時間に設定するという質問の提案は、UTCが動作し、どこでもALMOSTです。UTCオフセットの範囲は-12〜+14であるため、太平洋ではこのアプローチが失敗する場所がいくつかあります。私はこれらのデータ型をyyyymmdd形式の文字列として扱う傾向があり、2つの日付の間で比較計算を行う必要がある場合、これは文字列比較として安全に実行できます。デルタ比較(たとえば、日付と現在、またはX年齢に達するまでの期間)を行う場合、すべての日付が同じUTCオフセットで作成されていることを確認する必要があり、標準時間関数を使用して作業を行うことができます。


3
私はYYYYMMDD形式で、文字列としてこれらのデータ型を扱う傾向がある、と私は2つの日付の間の比較計算を行う必要がある場合は、これを安全に文字列比較として行うことができます。」ことを確認した音が好きなDateデータ型だけで運ばれていますaString
ロスパターソン

あなたが言うように、日付の文字列表現であり、元のポスターとは異なり、日付はUTC + 13タイムゾーンにあることによって変更されません。
マイケルショー

2

真の「日付のみ」のデータ型がないのはなぜですか?

同じ理由で、DateTime値は一般にUTCで指定されていると思います:シンプルさ信頼性。DateTime値のポイントは、タイムゾーン、夏時間、カレンダー、およびその他のローカル調整の影響を受けない単一のポイントを指定することです。DateTime値は、期間または時間のセットではなく、1つのインスタント(タイプの解像度の制限まで)を指定します。これらの制限により、DateTime値を信頼性が高く、予測可能で、簡単な方法で比較できます。

DateTime値で日付を指定しようとすると、ポイントを使用して領域を指定しようとするようなものです。「この点は半径100mの円の中心を表します」などの規則を使用してその作業を行うことができますが、そこには多くの問題があります。誰もが同じ規則を使用する必要があります。間違った型で作業する痛みを軽減するためのコードをサポートし、ある時点で従来の領域よりも大きいまたは小さい領域を指定する必要があることはほぼ保証されています。したがって、日付を使用します。日付を指定する従来の時刻として「正午」を使用できますが、人々はUTCではなく現地時間で日付を指定することを期待するため、タイムゾーンになります。また、DateTimeを使用して日付を指定するための満足のいく方法を考え出したとしても、それが絶対日付であるか相対日付であるかを知るために、より多くの情報が必要になります。1776年ですか、それとも毎年7月4日ですか?他の期間を使用して繰り返したい場合はどうしますか?また、カレンダーにはあらゆる種類の奇妙な問題があります。ある月は他の月より長く、ある年は他の月より長く、ある日は他の日よりも長く、いくつかのカレンダーにはギャップがあります。同じ問題が短期間で発生するため、これらの問題を丸1日だけ解決したくはありません。「4時間ごとに1ピル服用する」という表現を簡単に表現できるコードを書きたいと思うでしょう。グループは毎週金曜日に集います。」

そのため、日付の操作には多くの問題が伴います。ある時点を指定し、数値と同じように動作するタイプを提供することは比較的簡単(しゃれなし)ですが、日付が使用されるすべての方法に対応するタイプを提供することは非常に困難です。

他の人が指摘したように、そこにある日付の良いサポートを提供言語とライブラリは、それはそれは正確に正しい日付関連のコードを取得することは非常に難しい与えられ、それらを使用することがしばしば良い考えです。


2
「日付が使用されるすべての方法に対処するタイプを提供することは困難です。」確かに、すべてを行うために単一の型を提供しようとするのは恐ろしい考えです。最初のJavaリリースではjava.util.Dateのみが提供され、結果はひどいものでした。その後、彼らは複雑なjava.util.Calendar階層を追加しましたが、それほど良くなることはありませんでした。
ケビンクライン

1
@kevincline完全に同意します。OPは言語を指定しなかったので、一般性を目指していました。
カレブ

同じ理由で、DateTime値は一般にUTCで指定されていると思います」...ああ、それは本当だったでしょうか。それは2015年だし、作者のホームタイムゾーンを使用して書かれているコードの多くはまだある:-(
ロス・パターソン

1
日付を取り巻く一般に受け入れられている慣習がないのはなぜだろうと思っていました。「ポイントを使用してエリアを表す」ことは、私のフラストレーションを完全にカプセル化します。
マイケルブラックバーン

2

真の「日付のみ」のデータ型がないのはなぜですか?

さまざまな言語のさまざまなライブラリには、このようなタイプが多数あります。現在の言語にはほぼ確実に1つあります。Java utilパッケージには時間計算用の恐ろしいAPIがありましたが、java.timeパッケージの導入により、生活はずっと良くなりました。年月日値を含むjava.time.LocalDate、または月と日番号のみを含むjava.time.MonthDayを参照してください。


1

カレンダー操作は、コンピューティングの最も貧弱な側面の1つです。 このトピックに関する本はすべて書かれています。@MichealBlackburnは、日付のみのデータ型、つまりタイムライン上のポイントまで解決されず、再解釈の対象となるデータ型を求めるのに絶対的に正しいです。歴史的に、日付の意味については正当な論争がありました。グレゴリオ暦を採用することで、それがどれほど複雑になるかを知る必要があります。さらに、西ヨーロッパとその植民地でさえ、年が1月1日に常に始まっているわけではありません(たとえば、イギリスとイギリスアメリカは3月25日に始まりました)。


1
これは正しいです。私の答えのカレンダーよくある質問私の引用はclandar操作の複雑さとsubtletie4sを発見するための優れたリソースです
マイケル・ル・バルビエグリューネヴァルト

-2

に答えて:

正直なところ、ほとんどすべての言語がこのために1つのデータ型しか持っていない理由を知りたいと思います。

最も一般的な理由は、「必要ないため」かもしれません。時間、分、秒などを気にしない日付時刻が必要な場合は、次のように初期化するだけです。

date = new DateTime(year, month, day, 0, 0, 0);

必要に応じて、DateTimeを自分で拡張できます。

public class Date extends DateTime {
    ...
    public Date(int year, int month, int day) {
        this(year, month, day, 0, 0, 0);
    }
}

注:デフォルトの時間とタイムゾーンを意図的に無視しています。それらがすべてDateのsで同じである限り、何に設定するかは実際には関係ありません。UTCのケースを作成できます。あなたのサーバーが置かれているタイムゾーンを使用するケースを作ることができます-どちらの方法でも、のような不正確な値を表すことは重要ではないと思いますDate。デフォルト時刻と同じ-0にすることも、正午にすることもできます。関係ありません。Facebookが00:01に誕生日通知を送信したが、23:59に生まれた場合、私はあまり気にしません。そして、12時間以上休んでいることに気を悪くしません。

上記はJavaで記述されていますがDateTime、継承と継承のあるどの言語でも同様に機能します。Javaには実際にこれを解決する方法が数多くありますが、上記は非推奨です(Calendar今すぐ使用してください)。しかし、他の人がコメントに投稿したように、一部の言語は実際にDateクラスを提供ます。これはおそらくこの理由によるものと思われます。

Dateおそらく、すべての実装はおそらく言語の単なるラッパーでありDateTime、時間をゼロにします。そうしないと、2つのDate / DateTime間の日数、または2つDateのsが等しいかどうかなどの問題を解決するためにコードを複製する必要があります(2月29日と3月1日はどうですか?)。これらの種類のものは通常、DateTimeクラスで解決されます。に同じコードを再利用するのは理にかなっていDateます。


4
-1:年+月+日だけが必要な場合はLocalDateを使用します。その目的でDateTimeを使用すると、他のプログラマーがDateTimeを見て、それが瞬間を表すと想定する場合にバグにつながります。
ケビンクライン

@kevinclineこの質問は言語に依存しないので、それが必要だとは感じませんでした。また、「非推奨」というラベルの付いたコードを使用することは、自分でリスクを負うシナリオであることも明らかだと思います。さらに重要なことは、私は何かの例として、あなたは言語がどこシナリオで行うことができます使用されていない持っているLocalDate、またはDate型クラス、あなたは「ロール自分で自分の」に持っています。
シャズ

1
しかし、(物理的な時間とは対照的に)時間に関するビジネスルールを含む明確で簡潔で正しいコードには「必要です」。ライブラリが名目上の型を提供しない場合、プログラマが型を発明する必要があり、その方法は「DateTime」で始まりません。
ケビンクライン

@kevinclineコードがどのように明確または簡潔になるかわかりません。間のプログラマの観点からの違いは何だnew Date(2000, 1, 1);とはnew Date(2000, 1, 1);?空の時間、分、秒が下にあるのはどれかわかりますか?(setMinutes()のような)余分な関数が表示されるのが心配な場合は、DateラップDateTimeから継承する代わりにラップするルートをたどることができます。そして、setYear、setMonth、setDayなどのみを公開します。使用しているライブラリのDateTimeよりも正しい。
シャズ

私の背景は主にC#であり、LocalDateに類似した構造はありません。どうやら、DateTimeを処理しているだけです。
マイケルブラックバーン
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.