Вы можете сделать следующее,
# Create a dataframe where each element is aggregated as list
new_df = df.groupby('ID').agg(lambda x: pd.Series(x).unique().tolist())
# Generate column names to be used after expanding lists
country_cols = ['Country_'+str(i) for i in range(new_df["Country"].str.len().max())]
name_cols = ['Name_'+str(i) for i in range(new_df["Name"].str.len().max())]
# Drop the Country, Name columns from the original and expand Country, Name columns and concat that to the original dataframe, finally do a fillna
df2 = pd.concat(
[new_df.drop(['Country','Name'], axis=1),
pd.DataFrame.from_records(new_df["Country"], columns=country_cols, index=new_df.index),
pd.DataFrame.from_records(new_df["Name"], columns=name_cols, index=new_df.index)
], axis=1
).fillna(' ')