Вот что я предлагаю:
import pandas as pd
import numpy as np
df = pd.DataFrame({"user": ["tom", "tom", "tom", "bob", "bob", "bob", "alice", "mary"],
"email": ["tommy@email.com", "thomas@email.com", "tom@email.com", "bob123@email.com",
"bob123@email.com", " bobby@email.com", "alice@email.com", "mary@email.com"],
"day_dif": [-10, -2, 3, -11, 1, 2, 4, -5]})
# Treat case where no duplicates
df["dup"] = df["user"].duplicated(keep=False)
df["output"] = np.select([(df["dup"] == False) & (df["day_dif"] > 0),
(df["dup"] == False) & (df["day_dif"] < 0)],
["yes", "no"], default=np.NaN)
# Treat duplicates
temp = df.loc[df["dup"], :]
temp = temp.copy()
temp["neg"] = np.where(temp["day_dif"] < 0, temp["day_dif"], np.NaN)
idx = temp.groupby("user")["neg"].nlargest(1).reset_index().level_1
# Create grouping variable that will help us make comparison
temp["pos"] = np.where(temp.index.isin(idx), 1,(temp["day_dif"] > 0) * 1)
groups = (temp.groupby(['user', "pos"])["email"].apply(list).reset_index()
.sort_values(["user", "pos"]))
# compare all email in list by user and group pos
groups["output"] = groups["email"].apply(lambda x: all(w == x[0] for w in x))
# put on same line value for pos = 0 and pos = 1 for each user
groups["temp"] = groups["output"].shift(periods=-1)
# Apply your rules
groups["output"] = np.select([(groups.pos == 1) & (groups["output"] == False),
(groups.pos == 0) & (groups["temp"] == False)],
["yes", "yes"], default="no")
# reunite duplicates and non duplicates in one dataframe
new_df = pd.merge(df.loc[:, ["user", "email", "day_dif", "output"]],
groups[["user", "email", "output"]].explode(column="email"),
on=["user", "email"], how="outer")
new_df["output"] = np.where(new_df["output_y"].isnull(),
new_df["output_x"], new_df["output_y"])
new_df = new_df.drop(columns=["output_x", "output_y"]).drop_duplicates()
И вывод:
user email day_dif output
0 tom tommy@email.com -10 yes
1 tom thomas@email.com -2 yes
2 tom tom@email.com 3 yes
3 bob bob123@email.com -11 yes
5 bob bob123@email.com 1 yes
7 bob bobby@email.com 2 yes
8 alice alice@email.com 4 yes
9 mary mary@email.com -5 no