Here is my take on your interesting question.
You can define a helper function:
def to_datetime(df, col, excluded_patterns):
"""Convert df[col] to datetime.
Args:
df: target dataframe.
col: target column.
excluded_patterns: regex date patterns to exclude from being converted.
'\d' means any digit, '\d{4}' means 4 consecutive digits.
"\d{2}-\d{2}-\d{4}" correspond to "05-21-2018" for instance.
Returns:
dataframe with 'col' values converted to datetime if not excluded.
"""
df_ = df.copy()
if not excluded_patterns:
df_[col] = pd.to_datetime(df_[col], infer_datetime_format=True, errors="ignore")
return df_
excluded = pd.concat(
[df_.loc[df[col].str.fullmatch(pat), :] for pat in set(excluded_patterns)]
)
df_ = df_.loc[~df.index.isin(excluded.index), :]
df_[col] = pd.to_datetime(df_[col], infer_datetime_format=True, errors="ignore")
return pd.concat([df_, excluded]).sort_index()
And then, with the following toy dataframe:
import pandas as pd
df = pd.DataFrame(
{"dates": ["21-5-2018", "21-5-18", "05/21/2018", "5/21/2018", "2018--05-21"]}
# Regular use cases
print(to_datetime(df, "dates", [r"\d{1,2}-\d-\d{4}"]))
dates
0 21-5-2018
1 2018-05-21 00:00:00
2 2018-05-21 00:00:00
3 2018-05-21 00:00:00
4 2018-05-21 00:00:00
print(to_datetime(df, "dates", [r"\d{1,2}-\d-\d{4}", r"\d{1,2}-\d-\d{2}"]))
dates
0 21-5-2018
1 21-5-18
2 2018-05-21 00:00:00
3 2018-05-21 00:00:00
4 2018-05-21 00:00:00
# Edge cases
print(to_datetime(df, "dates", [])) # No pattern
dates
0 2018-05-21
1 2018-05-21
2 2018-05-21
3 2018-05-21
4 2018-05-21
print(to_datetime(df, "dates", [r"\d-\d-\d"])) # Pattern not found
dates
0 2018-05-21
1 2018-05-21
2 2018-05-21
3 2018-05-21
4 2018-05-21
print(to_datetime(df, "dates", [r"\d{1,2}-\d-\d{4}", r"\d-\d-\d"])) # One pattern found, one not found
dates
0 21-5-2018
1 2018-05-21 00:00:00
2 2018-05-21 00:00:00
3 2018-05-21 00:00:00
4 2018-05-21 00:00:00
print(to_datetime(df, "dates", [r"\d{1,2}-\d-\d{4}", r"\d{1,2}-\d-\d{4}"])) # Twice the same pattern
dates
0 21-5-2018
1 2018-05-21 00:00:00
2 2018-05-21 00:00:00
3 2018-05-21 00:00:00
4 2018-05-21 00:00:00