def shift_isochrone(color, magnitude, distance : float, extinction : float): mu = 5*np.log10(distance) - 5 + extinction aptMag = mu + magnitude aptCol = 3.2*extinction + color return aptMag, aptCol def interp_isochrone_age(iso, targetAge): logTargetAgeYr= np.log10(targetAge*1e9) ageKeys = list(iso.keys()) distance = [(x-logTargetAgeYr, x) for x in ageKeys] below = sorted(filter(lambda x: x[0] <=0, distance), key=lambda x: abs(x[0])) above = sorted(filter(lambda x: x[0] > 0, distance), key=lambda x: x[0]) isoBelow = iso[below[0][1]] isoAbove = iso[above[0][1]] age1 = isoBelow['log10_isochrone_age_yr'].iloc[0] age2 = isoAbove['log10_isochrone_age_yr'].iloc[0] def linearinterpolate(x, other, age1, age2): newIso = ((other[x.name] - x)/(age2-age1)) * (logTargetAgeYr - age1) + x return newIso interpolated = isoBelow.apply(lambda x: linearinterpolate(x, isoAbove, age1, age2)) return interpolated, (isoBelow, isoAbove) def iso_at_params(iso, age, d, E, f1, f2, f3): interpolated, _= interp_isochrone_age(iso, age) f1 = interpolated[f"WFC3_UVIS_{f1}_MAG"] f2 = interpolated[f"WFC3_UVIS_{f2}_MAG"] f3 = interpolated[f"WFC3_UVIS_{f3}_MAG"] return shift_isochrone(f1-f2, f3, d, E)