Это можно сделать с помощью трансляции:
mask = ((sample_df.begin.values<=date_series.values[:,None]) &
(date_series.values[:,None]<= sample_df.end.values))
np.where(mask, sample_df.index.values[None,:], np.nan)
Вывод:
array([[ 0., nan, 2., 3., 4., 5., 6., 7., 8., 9.],
[ 0., nan, nan, 3., 4., nan, 6., 7., nan, 9.],
[ 0., 1., 2., 3., 4., 5., 6., 7., 8., 9.],
[ 0., nan, nan, 3., 4., nan, 6., 7., nan, 9.],
[nan, nan, nan, 3., nan, nan, 6., 7., nan, 9.],
[nan, nan, nan, 3., nan, nan, 6., 7., nan, 9.],
[ 0., nan, nan, 3., nan, nan, 6., 7., nan, 9.],
[ 0., nan, nan, 3., 4., nan, 6., 7., nan, 9.],
[nan, nan, nan, nan, nan, nan, nan, nan, nan, nan],
[nan, nan, nan, nan, nan, nan, nan, nan, nan, nan]])