diff options
-rw-r--r-- | src/solar.py | 126 |
1 files changed, 121 insertions, 5 deletions
diff --git a/src/solar.py b/src/solar.py index a7815de..ead1653 100644 --- a/src/solar.py +++ b/src/solar.py @@ -203,7 +203,7 @@ def sun_geometric_mean_longitude(t): @return :float The Sun's geometric mean longitude in radians ''' return radians((0.0003032 * t ** 2 + 36000.76983 * t + 280.46646) % 360) - # CANNIBALISERS and TIME TRAVELERS: + # CANNIBALISERS: # The result of this function should always be positive, this # means that after division modulo 360 but before `radians`, # you will need to add 360 if the value is negative. This can @@ -437,8 +437,17 @@ def solar_elevation(latitude, longitude, t = None): return degrees(rc) -# TODO document and demo + +# TODO document def have_sunrise_and_sunset(latitude, t = None): + ''' + Determine whether solar declination currently is so that there can be sunrises and sunsets. + If not, you either have 24-hour daytime or 24-hour nighttime. + + @param latitude:float The latitude in degrees northwards from the equator, negative for southwards + @param t:float? The time in Julian Centuries, `None` for the current time + @return Whether there can be sunrises and sunsets where you are located + ''' t = julian_centuries() if t is None else t d = degrees(solar_declination(t)) ## Covert everything to the Northern hemisphere @@ -453,6 +462,13 @@ def have_sunrise_and_sunset(latitude, t = None): # TODO document def is_summer(latitude, t = None): + ''' + Determine whether it is summer + + @param latitude:float The latitude in degrees northwards from the equator, negative for southwards + @param t:float? The time in Julian Centuries, `None` for the current time + @return Whether it is summer on the hemisphere you are located on + ''' t = julian_centuries() if t is None else t d = solar_declination(t) return (d > 0) == (latitude > 0) @@ -460,13 +476,32 @@ def is_summer(latitude, t = None): # TODO document def is_winter(latitude, t = None): + ''' + Determine whether it is winter + + @param latitude:float The latitude in degrees northwards from the equator, negative for southwards + @param t:float? The time in Julian Centuries, `None` for the current time + @return Whether it is winter on the hemisphere you are located on + ''' t = julian_centuries() if t is None else t d = solar_declination(t) return not ((d > 0) == (latitude > 0)) + # TODO document def solar_prediction(delta, requested, fun, epsilon = 0.000001, span = 0.01, t = None): + ''' + Predict the time point of the next or previous time an arbitrary condition is meet + + @param delta:float Iteration step size, negative for past event, positive for future event + @param requested:float The value returned by `fun` for which to calculate the time point of occurrence + @param fun:(t:float)→float Function that calculate the data of interest + @param epsilon:float Error tolerance for `requested` + @param span:float The number of Julian centuries (0,01 for one year) to restrict the search to + @param t:float? The time in Julian Centuries, `None` for the current time + @return :float? The calculated time point, `None` if none were found within the specified time span + ''' t = julian_centuries() if t is None else t t1 = t2 = t v1 = v0 = fun(t) @@ -501,23 +536,53 @@ def solar_prediction(delta, requested, fun, epsilon = 0.000001, span = 0.01, t = return None + # TODO document def future_past_equinox(delta, t = None): + ''' + Predict the time point of the next or previous equinox + + @param delta:float Iteration step size, negative for past event, positive for future event + @param t:float? The time in Julian Centuries, `None` for the current time + @return :float The calculated time point + ''' return solar_prediction(delta, 0, solar_declination, t = t) # TODO document def future_equinox(t = None): + ''' + Predict the time point of the next equinox + + @param delta:float Iteration step size, negative for past event, positive for future event + @param t:float? The time in Julian Centuries, `None` for the current time + @return :float The calculated time point + ''' return future_past_equinox(0.01 / 2000, t) # TODO document def past_equinox(t = None): + ''' + Predict the time point of the previous equinox + + @param delta:float Iteration step size, negative for past event, positive for future event + @param t:float? The time in Julian Centuries, `None` for the current time + @return :float The calculated time point + ''' return future_past_equinox(0.01 / -2000, t) + # TODO document def future_past_solstice(delta, t = None): + ''' + Predict the time point of the next or previous solstice + + @param delta:float Iteration step size, negative for past event, positive for future event + @param t:float? The time in Julian Centuries, `None` for the current time + @return :float The calculated time point + ''' e = 0.00001 fun = lambda t : (solar_declination(t + e) - solar_declination(t - e)) / 2 return solar_prediction(delta, 0, fun, t = t) @@ -525,14 +590,27 @@ def future_past_solstice(delta, t = None): # TODO document def future_solstice(t = None): + ''' + Predict the time point of the next solstice + + @param t:float? The time in Julian Centuries, `None` for the current time + @return :float The calculated time point + ''' return future_past_solstice(0.01 / 2000, t) # TODO document def past_solstice(t = None): + ''' + Predict the time point of the previous solstice + + @param t:float? The time in Julian Centuries, `None` for the current time + @return :float The calculated time point + ''' return future_past_solstice(0.01 / -2000, t) + def future_past_elevation(delta, latitude, longitude, elevation, t = None): ''' Predict the time point of the next or previous time the Sun reaches or reached a specific elevation @@ -542,7 +620,7 @@ def future_past_elevation(delta, latitude, longitude, elevation, t = None): @param longitude:float The longitude in degrees eastwards from Greenwich, negative for westwards @param elevation:float The elevation of interest @param t:float? The time in Julian Centuries, `None` for the current time - @return :float The calculated time point, `None` if none were found within a year + @return :float? The calculated time point, `None` if none were found within a year ''' return solar_prediction(delta, elevation, lambda t : solar_elevation(latitude, longitude, t), t = t) @@ -555,7 +633,7 @@ def future_elevation(latitude, longitude, elevation, t = None): @param longitude:float The longitude in degrees eastwards from Greenwich, negative for westwards @param elevation:float The elevation of interest @param t:float? The time in Julian Centuries, `None` for the current time - @return :float The calculated time point, `None` if none were found within a year + @return :float? The calculated time point, `None` if none were found within a year ''' return future_past_elevation(0.01 / 2000, latitude, longitude, elevation, t) @@ -568,13 +646,24 @@ def past_elevation(latitude, longitude, elevation, t = None): @param longitude:float The longitude in degrees eastwards from Greenwich, negative for westwards @param elevation:float The elevation of interest @param t:float? The time in Julian Centuries, `None` for the current time - @return :float The calculated time point, `None` if none were found within a year + @return :float? The calculated time point, `None` if none were found within a year ''' return future_past_elevation(0.01 / -2000, latitude, longitude, elevation, t) + # TODO document def future_past_elevation_derivative(delta, latitude, longitude, elevation_derivative, t = None): + ''' + Predict the time point of the next or previous time the Sun reaches or reached a specific elevation derivative + + @param delta:float Iteration step size, negative for past event, positive for future event + @param latitude:float The latitude in degrees northwards from the equator, negative for southwards + @param longitude:float The longitude in degrees eastwards from Greenwich, negative for westwards + @param elevation_derivative:float The elevation derivative value of interest + @param t:float? The time in Julian Centuries, `None` for the current time + @return :float? The calculated time point, `None` if none were found within a year + ''' fun = lambda t : solar_elevation(latitude, longitude, t) dfun = lambda t : (fun(t + e) - fun(t - e)) / 2 return solar_prediction(delta, elevation_derivative, dfun, t = t) @@ -582,14 +671,33 @@ def future_past_elevation_derivative(delta, latitude, longitude, elevation_deriv # TODO document def future_elevation_derivative(latitude, longitude, elevation_derivative, t = None): + ''' + Predict the time point of the next time the Sun reaches a specific elevation derivative + + @param latitude:float The latitude in degrees northwards from the equator, negative for southwards + @param longitude:float The longitude in degrees eastwards from Greenwich, negative for westwards + @param elevation_derivative:float The elevation derivative value of interest + @param t:float? The time in Julian Centuries, `None` for the current time + @return :float? The calculated time point, `None` if none were found within a year + ''' return future_past_elevation_derivative(0.01 / 2000, latitude, longitude, elevation_derivative, t) # TODO document def past_elevation_derivative(latitude, longitude, elevation_derivative, t = None): + ''' + Predict the time point of the previous time the Sun reached a specific elevation derivative + + @param latitude:float The latitude in degrees northwards from the equator, negative for southwards + @param longitude:float The longitude in degrees eastwards from Greenwich, negative for westwards + @param elevation_derivative:float The elevation derivative value of interest + @param t:float? The time in Julian Centuries, `None` for the current time + @return :float? The calculated time point, `None` if none were found within a year + ''' return future_past_elevation_derivative(0.01 / -2000, latitude, longitude, elevation_derivative, t) + # TODO: This algorithm is imprecise, gives an incorrent sunrise and I do not fully know its behaviour def sunrise_equation(latitude, longitude, t = None): j_cent = julian_centuries() if t is None else t @@ -612,8 +720,16 @@ def sunrise_equation(latitude, longitude, t = None): return (julian_day_to_julian_centuries(sunset), julian_day_to_julian_centuries(sunrise)) + # TODO document def ptime(t): + ''' + Print a time stamp in human-readable local time + + This function is intended for testing + + @param t The time stamp in Julian Centuries + ''' import datetime print(str(datetime.datetime.fromtimestamp(int(julian_centuries_to_epoch(t))))) |