[HN Gopher] Show HN: Moon Phase Algorithms for C, Lua, Awk, Java...
___________________________________________________________________
Show HN: Moon Phase Algorithms for C, Lua, Awk, JavaScript, etc.
Author : oliverkwebb
Score : 60 points
Date : 2025-06-01 23:22 UTC (23 hours ago)
(HTM) web link (github.com)
(TXT) w3m dump (github.com)
| ericpruitt wrote:
| I adapted the same moonphase logic for the status line program I
| use with dwm. Did you run into any discrepancies with using
| January 0 vs December 31st? Some of the translations of Walker's
| as noted in my comment at
| https://github.com/ericpruitt/emus/blob/ea059239845ee6d57614...
| seem to produce differing results.
| oliverkwebb wrote:
| This discrepancy with time is explained in the book the
| algorithm is based on (Practical Astronomy with Your
| Calculator, which also does a good job explaining a ton of
| other ideas and models in astronomical calculation).
|
| January 0th makes sense because a year starts on January 1st.
| You count days of the year from 1 instead of from 0. So if we
| are going by the day of the year, day 1 of the year should be
| Jan1, the consequence of this being that Jan0 exists and is
| Dec31 of the prev year.
|
| I originally got into this because of my status bar on i3,
| hacking together C code from moontool into
| https://github.com/oliverkwebb/moontool about a year back.
| rybosome wrote:
| Fun! From the repo[0]:
|
| > Your function must be self-contained, such that someone could
| copy-paste it into their code and not get an error. It also must
| not effect the environment outside it if at all possible (no
| #define or mutating globals). It must be as "pure" and self-
| contained as the language will allow.
|
| This is an interesting restriction, actually, with respect to
| style. The "natural" way I would program such an algorithm
| certainly doesn't adhere to this requirement.
|
| Producing functions that are still correct, idiomatic and legible
| while producing minimal changes to environment or state requires
| a non-beginners understanding of the runtime nature of the
| language.
|
| [0]: https://github.com/oliverkwebb/moonphase?tab=readme-ov-
| file#...
| danparsonson wrote:
| Could you elaborate on this? Maybe an example of what you mean?
| oliverkwebb wrote:
| This is also interesting for speed, The algorithms ran by all
| the impls are identical, but sacrificing speed for cleanliness
| and adherence to spirit is done regularly.
|
| Without having actually measured, the rust impl probably runs
| faster than the C impl, but that's not because rust is "faster"
| than C. That's because I used a closure with one call to
| floor() for modulus in rust, whilst in C I did 2 fmod()'s to
| get it because the alternative would've been to make the code
| unreadable or add a second function/macro (although thinking
| about it now, undef does exist...)
| blululu wrote:
| This is really nice. My initial thought was "why just divide the
| time interval since the Unix Epoch by the synodic period of the
| moon". Turns out the moon's phase is a bit more complicated than
| that. https://en.wikipedia.org/wiki/Lunar_phase#Calculating_phase
| madcaptenor wrote:
| That said, this is basically what the Hebrew calendar does
| (although of course they use a much earlier epoch)
| o11c wrote:
| `pom(6)` from `bsdgames` might already be installed on your
| system to do this. Source comments indicate it was originally
| based on prior versions of the same book but updated to the Third
| Edition in 1998.
|
| For "implement simple task in many languages" you should probably
| think of Rosetta Code, now at
| https://rosettacode.miraheze.org/wiki/Rosetta_Code
| lifthrasiir wrote:
| This code consistently converts angles to the [0, 360) range,
| which is IMO overkill. A better approach is to normalize
| everything to [0, 2) range so that you can simply multiply or
| divide by pi to get the radians. If your math library has `sinpi`
| or `cospi` it will be even more accurate, as it no longer has to
| divide by 2pi to do the actual calculation.
| librasteve wrote:
| made a PR for raku, hope it gets accepted
|
| some cool things stood out: sub fixangle($a) { $a
| mod 360 } # raku has built-in support for Euclidean modulo
| pi # raku has pi #
| Solve equation of Kepler my $e = $M; my $delta;
| repeat { # raku's repeat loop allows
| initialisation of delta to be folded in $delta = $e -
| $eccent * sin($e) - $M; $e -= $delta / (1 - $eccent *
| cos($e)); } while abs($delta) > 1e-6;
| eddyg wrote:
| Thanks! (I'm a big fan of Raku; it doesn't get nearly the
| respect it deserves!)
| oliverkwebb wrote:
| Thank you! I accepted it
| librasteve wrote:
| yay - it has made it to raku module status
| https://raku.land/zef:librasteve/Moonphase
| anthk wrote:
| AWK can be far more than a DSL.
| kbr2000 wrote:
| LCAL[0]: The Moon Phase Calendar Program
|
| A PostScript program to visualize a calendar of moon phases (skip
| down to "LCAL PostScript Calendar Examples" for just that). Did
| some nice PS prints recently for the next 10 years, adapted to
| fit in a frame I had laying around.
|
| [0] https://pcal.sourceforge.net/
___________________________________________________________________
(page generated 2025-06-02 23:02 UTC)