Hitung Fase Bulan

10

pengantar

tl; dr

Dalam tantangan ini, Anda harus menghitung fase bulan untuk tanggal tertentu.


Tantangan ini terinspirasi oleh eksperimen audiovisual sosial psiko permainan " Superbrothers: Sword & Sworcery EP ". Dalam S: S&S EP fase bulan penting untuk hasil petualangan karena beberapa peristiwa hanya terjadi pada titik waktu tertentu.

Cuplikan layar dari Superbrothers: Sword & Sworcery EP

Pertanyaannya adalah: Fase bulan mana yang ada pada tanggal tertentu. Setiap fase utama - dari bulan baru ke kuartal pertama ke bulan purnama ke kuartal ketiga - adalah sekitar 7,38 hari. Seluruh siklus bulan sekitar 29,52 hari. Berdasarkan nilai-nilai ini berbagai metode perhitungan ada. 1

Memasukkan

  • Tanggal berdasarkan kalender Gregorian, antara 1 Januari 1970 dan 31 Desember 2116.
  • Anda dapat memilih salah satu dari format berikut: yyyy-mm-dd, dd.mm.yyyy, dd/mm/yyyy, yyyymmddatau ddmmyyyy.

Keluaran

Keluarkan indeks [0-7]fase bulan berdasarkan pada array yang diindeks nol ini:

['New moon', 'Waxing crescent', 'First quarter', 'Waxing gibbous', 'Full moon', 'Waning gibbous', 'Third quarter', 'Waning crescent`]

Persyaratan

  • Anda dapat menulis suatu program atau fungsi. Jika Anda menggunakan fungsi anonim, harap sertakan contoh cara menjalankannya.
  • Masukan diterima dari STDIN , argumen baris perintah, sebagai parameter fungsi atau dari padanan terdekat.
  • Ini adalah sehingga jawaban terpendek dalam byte menang.
  • Perpustakaan internal atau eksternal yang menghitung fase bulan tidak diperbolehkan. 2
  • Celah standar tidak diijinkan.

Tes

Nilai-nilainya adalah: date | index of the phase | illumination | name

Siklus bulan penuh:

08.02.2016 | 0 |   0% | New moon
07.02.2016 | 7 |   2% | Waning crescent
07.02.2016 | 7 |   2% | Waning crescent
06.02.2016 | 7 |   6% | Waning crescent
05.02.2016 | 7 |  12% | Waning crescent
04.02.2016 | 7 |  19% | Waning crescent
03.02.2016 | 7 |  28% | Waning crescent
02.02.2016 | 7 |  37% | Waning crescent
01.02.2016 | 6 |  47% | Third quarter
31.01.2016 | 5 |  56% | Waning gibbous
30.01.2016 | 5 |  65% | Waning gibbous
29.01.2016 | 5 |  74% | Waning gibbous
28.01.2016 | 5 |  82% | Waning gibbous
27.01.2016 | 5 |  89% | Waning gibbous
26.01.2016 | 5 |  94% | Waning gibbous
25.01.2016 | 5 |  98% | Waning gibbous
24.01.2016 | 4 | 100% | Full moon
23.01.2016 | 3 | 100% | Waxing gibbous
22.01.2016 | 3 |  97% | Waxing gibbous
21.01.2016 | 3 |  93% | Waxing gibbous
20.01.2016 | 3 |  86% | Waxing gibbous
19.01.2016 | 3 |  77% | Waxing gibbous
18.01.2016 | 3 |  67% | Waxing gibbous
17.01.2016 | 3 |  56% | Waxing gibbous
16.01.2016 | 2 |  45% | First quarter
15.01.2016 | 1 |  33% | Waxing crescent
14.01.2016 | 1 |  23% | Waxing crescent
13.01.2016 | 1 |  14% | Waxing crescent
12.01.2016 | 1 |   7% | Waxing crescent
11.01.2016 | 1 |   2% | Waxing crescent
10.01.2016 | 0 |   0% | New moon

Kasus uji acak:

14.12.2016 | 4 | 100% | Full moon
16.10.1983 | 3 |  75% | Waxing gibbous
04.07.1976 | 2 |  47% | First quarter
28.11.1970 | 0 |   0% | New moon

Karena sebagian besar metode tidak akurat untuk tingkat ilmiah dan Anda juga mendapatkan hasil yang beragam di situs web yang berbeda untuk beberapa hari ini, itu dapat diterima jika hasil Anda berada dalam kisaran ± 1 hari .

Bonus

Kurangi jumlah byte Anda dan tarik :

  • 15% - Cetak nama fase yang sebenarnya sebagaimana tercantum di bagian Output, bukan indeksnya.
  • 25% - Cetak tanggal bulan baru dan bulan purnama yang akan datang dipisahkan oleh spasi putih atau baris baru pada input kosong.

1 Misalnya: Menghitung fase di Wikipedia.
2 Sorry Mathematica .

masukkan nama pengguna di sini
sumber
Uangku ada di Japt.
lirtosiast
Berapa lama setiap fase bertahan? Anda merujuk pada empat fase utama yang berlangsung sekitar 7 hari, tetapi ada 8 fase yang harus dihadapi.
Sherlock9
1
Saya pikir untuk membantu saya memahami berapa lama setiap fase seharusnya, dapatkah Anda memposting uji kasus sekitar lima hari berturut-turut, atau berapa lama waktu yang diperlukan untuk berubah, dari, "waxing gibbous" menjadi "waning gibbous" dengan perhitungan Anda? Saya mengalami masalah dengan definisi karena, misalnya, seperempat bulan adalah instan dari pencahayaan 50%, jadi "kuartal pertama" seharusnya hanya pada hari itu sendiri, dengan "waxing sabit" dan "memudarnya bulan sabit" pada hari-hari sebelumnya dan setelah. Tapi saya tidak yakin.
Sherlock9
Baiklah, saya akan memulai solusi saya. Terima kasih telah membereskan beberapa hal ini.
Sherlock9
@ Sherlock9 Saya telah memperbarui kasus uji dengan siklus bulan penuh dan beberapa nilai acak, termasuk iluminasi setiap hari. Semoga ini bermanfaat.
masukkan nama pengguna di sini

Jawaban:

3

Python 2 3, 255 204 180 178 byte

Ini adalah jawaban yang tidak akurat oleh satu atau dua hari di beberapa tempat, termasuk untuk beberapa kasus uji, meskipun saya diberitahu bahwa beberapa ketidakakuratan dapat diterima. Bagaimanapun, gerakan bulan tidak pernah sangat tepat dan fungsi ini secara umum tetap benar (atau setidaknya, itu tidak berbeda terlalu jauh).

Sunting: Dalam rangka memperbaiki kode saya dan membuatnya lebih akurat, saya telah menurunkannya.

Sunting: Kode ini sekarang adalah program Python 3 satu baris. (Kredit untuk TimmyD untuk nama "angka ajaib")

p,q,r=(int(i)for i in input().split("-"));t=q<3;y=p-2000-t;i,j=divmod(((r+(153*(q+12*t-3)+2)//5+365*y+y//4-y//100+y//400+11010)*86400-74100)%2551443,637861);print((86400<=j)+2*i)

Tidak Disatukan:

def jul(p,q,r):
    '''
    The Julian Day Number (JDN) of the input minus the JDN of January 7, 1970,
    the first new moon after January 1, 1970.
    '''
    t=q<3
    y=p-2000-t  # -2000 years to push day 0 to January 1, 2000
    return r+(153*(q+12*t-3)+2)//5+365*y+y//4-y//100+y//400+11010
    # +11010 days to push day 0 to January 7, 1970

def moon(s):
    '''
    Input format: yyyy-mm-dd

    An attempt at explaining the "magic numbers"
    - 29.53059 days is close to 2551443 seconds, so I used that
    - The offset of +12300 seconds because the new moon of 1970-01-07 was at 2035 UTC 
      or 12300 seconds before midnight. For those of you saying that this pushes 
      the beginning of my calendar to 2035, *6* January 1970, yes it does.
      But if I need to the calendar to recognize 1970-01-07 as the day of the new moon 
      which means that midnight needed to be a positive number of seconds, 0 <= x < 86400.
      Basically, I hacked it together, and +12300 worked.        
    '''
    d = 86400
    p,q,r = map(int, s.split("-"))
    z=(jul(p,q,r)*d+12300)%2551443  # 2551443 is about the number of seconds in a lunar month
    div, mod = divmod(z, 637861)    # 637861 seconds is about a quarter of a lunar month
                                    # div is what part of the lunar month this is (0 - 3)
                                    # mod is seconds since the start of the main phase
    return 2*div + (86400 <= mod)   # 2*div for the main phase, and 
                                    # is mod >= the number seconds in a day?
                                    # (+0 if within a day of the main phase, +1 otherwise)
Sherlock9
sumber
@TimmyD Anda tidak tahu berapa banyak angka ajaib yang saya coba dan buang agar XD berfungsi
Sherlock9