

こちらで指定する4桁の日付の記載方法から、存在している日付かどうかをチェックをしたいです。

例えば8月23日だったら0823のような感じで、こちらは実際に存在している日付なのですが、9999のような実際にありえない日付だった場合、エラーを出すようにしたいです。  
4桁と数字のチェックから、4桁の数字が存在する日付なのかをチェックするにはどのようにすればいいかご教授いただければ幸いです。

[code]

    time=input("日付を入力をしてください：")
    if len(time)==4 :
        if time.isdigit()==True:
            print("正常")
        else:
            print("数字ではありません")
    else:
        print("桁数が違います")
    
[/code]


CC BY-SA 4.0
2022-08-23T02:48:31.337
90703
2023-09-07T07:59:12.457
2022-08-23T09:00:17.053
3060
54115
question
python python3
入力された日付が正しいものかチェックするには？


"python date validation" で google 検索すると、例えば以下のページがヒットします。

[How do I validate a date string format in python? - Stack
Overflow](https://stackoverflow.com/q/16870663/2322778)

[回答の一つ](https://stackoverflow.com/a/16870690/2322778) を参考にすると、datetime
モジュールを使った以下のような方法が紹介されています。

>
[code]

>     from datetime import datetime
>  
>     datetime.strptime(date_string, "%Y-%m-%d")
>  
[/code]

もし不正な日付が指定された場合は `ValueError` が発生するので、`try` と `expect` を使って例外処理を書いてやればよさそうです。

今回の質問の例に当てはめるなら、日付のフォーマット指定の部分は以下の様になります。

[code]

    datetime.strptime(date_string, "%m%d")
    
[/code]


CC BY-SA 4.0
2022-08-23T04:19:30.263
90706
2022-08-23T04:19:30.263
3060
90703
answer


変則的なコードですが、正規表現で妥当性チェックする方法もあります。  
下記のコードでは、`is_date`関数に文字列を渡すと、4桁の月日文字列(うるう年の"0229"を含む)ならばTrueを返します。

[code]

    import re
    
    def is_date(s: str) -> bool:
        pattern = re.compile("(01|03|05|07|08|10|12)(0[1-9]|[12][0-9]|3[01])$|"  # 31日までの月 \
                             "(04|06|09|11)(0[1-9]|[12][0-9]|30)$|"              # 30日までの月 \
                             "(02(0[1-9]|[12][0-9]))$")                          # 29日までの月
        return pattern.match(s) != None
    
    # 正常データ
    assert is_date("0101")
    assert is_date("0229")
    assert is_date("0430")
    assert is_date("1231")
    
    # 異常データ
    assert is_date("0000") == False
    assert is_date("0132") == False
    assert is_date("0230") == False
    assert is_date("1301") == False
    assert is_date("9999") == False
    assert is_date("101") == False
    assert is_date("01011") == False
    assert is_date("OIOI") == False
    
[/code]

**参考資料**

[yyyymmdd形式日付文字列の妥当性をチェックする正規表現を読み解く](https://qiita.com/shojit/items/c633a329dbbcc56923d6)


CC BY-SA 4.0
2022-08-23T08:05:08.793
90716
2022-08-23T08:05:08.793
9820
90703
answer


以下は Pandas モジュールの `to_datetime()` を使う方法です。

[code]

    import pandas as pd
    
    def validate_date_string(date_str):
        return len(date_str) == 4 and \
               pd.to_datetime(f'2000{date_str}', format='%Y%m%d', errors='coerce') is not pd.NaT
    
    if __name__ == '__main__':
        testing = ['0801', '0229', '9999', '', 'abcd']
        for t in testing:
            print(validate_date_string(t))
    
[/code]


CC BY-SA 4.0
2022-08-23T09:46:24.107
90719
2022-08-23T09:46:24.107
47127
90703
answer