Hari apa hari ini (atau tanggal lainnya)?


12

Tugas

Tulis program atau fungsi yang menghitung nama hari-hari dari tanggal yang dimasukkan pengguna.

Input output

Input adalah string YYYYMMDD,.

Contoh nilai input:

20110617: 17 Juni 2011
19040229: 29 Februari 1904
06661225: 25 Desember 666
00000101: 1 Januari 0
99991231: 31 Desember 9999

Anda dapat mengasumsikan bahwa semua input valid. Perhatikan bahwa tahun nol adalah valid.

Output adalah bilangan bulat antara 0dan 6. Setiap bilangan bulat mewakili nama hari kerja. Anda dapat memutuskan bilangan bulat mana yang mewakili nama hari kerja, seperti ini

0: Senin
1: Selasa
2: Rabu
...
6: Minggu

(dalam urutan) atau yang ini

0: Senin
1: Rabu
2: Minggu
...
6: Sabtu

(tidak berurutan).

Uji Kasus

Input Output Hari-Hari ([0..6 -> Senin..Sunday] digunakan dalam contoh ini.)

20110617 Jumat 4
19500101 Minggu 6
22220202 Sabtu 5
19000228 Rabu 2
19000301 Kamis 3
19450815 Rabu 2
19040229 Senin 0
19040301 Selasa 1
17760704 Kamis 3
20000228 Senin 0
20000229 Selasa 1
20000301 Rabu 2
20121223 Minggu 6
00000401 Sabtu 5
66660606 Rabu 2
59161021 Sabtu 5

Larangan

Anda tidak boleh menggunakan segala jenis fungsi / kelas / ... yang terkait dengan stempel waktu atau tanggal, seperti Datekelas di Java/ JavaScript/ ActionScript, atau getdatefungsi dalam PHP.

Anda harus menggunakan kalender Gregorian , yang digunakan oleh banyak orang sekarang.

Tentu saja, kode terpendek menang. Jika dua kode memiliki panjang yang sama, maka kode dengan suara terbanyak menang.

(Jatuh tempo: Ketika ada lebih dari 5 kode yang memiliki lebih dari (atau setara) +1suara.)


Hari ini? Kenapa, Hari Natal!
Joey Adams

3
Solusi Optimis ditulis dalam Bash (6 karakter): echo 4.
kebenaran

1
@trutheality Tidak, saya tidak bermaksud seperti itu. Yang saya inginkan adalah kode yang mencetak / mengembalikan hari dalam seminggu dari tanggal seseorang mengetik, bukan hanya mencetak hari dalam seminggu hari ini.
JiminP

Oh saya tahu. Itulah yang dilakukan orang ini.
kebenaran

Benar setidaknya 14% dari waktu!
Draco18s tidak lagi mempercayai SE

Jawaban:


2

Ruby, 95 92 karakter

Implementasi ruby ​​langsung polos dengan 0: Senin, ...

p ((y=(d=gets.to_i)/(k=100)/k-((m=d/k%k)<3?1:0))+y/4-y/k+y/400+"squsptrotqro"[-m].ord+d%k)%7

4

PHP - 101 97 103 125 karakter

  • Algoritma Sakamoto
  • 0 = Minggu

Kode

<?php fscanf(STDIN,"%4d%2d%2d",$y,$m,$d);@$a=a032503514624;$y-=$m<3;$z=$y+1;echo($y+$y/4%$z-$y/100%$z+$y/400%$z+$a[$m]+$d)%7;

Catatan

Sayangnya, karena dinamis, lemah mengetik PHP, algoritma Sakamoto tidak berfungsi dengan baik tanpa secara eksplisit lantai operasi masing-masing divisi.


Bisakah Anda menguji lagi? Selama beberapa tahun ini memberi saya hasil yang berbeda (mis. Testcase 17760704 menghasilkan Selasa bukan Rabu).
Howard

@ Bagaimana itu sangat aneh; untuk 17760704, saya mendapatkan hari Rabu. Saya mendapatkan inkonsistensi lain, yang tidak dapat saya pertanggungjawabkan, misalnya 19040229 kembali pada hari Selasa. Tidak yakin apa yang menyebabkan ini. Saya mendapatkan hasil yang sama ketika saya mengembangkan kembali algoritma y+y/4-y/100+y/400.
rintaun

Saya bisa melihatnya terjadi dengan 497 * y / 400: y=4dalam kasus itu mengembalikan 4, bukan 5 yang benar dari y+y/4+y/100+y/400(di mana hanya dua istilah pertama ikut bermain). Itulah yang mengganggu jawaban JavaScript saya. Apakah mungkin dobel dibuat bukan int? (PHP saya terlalu lemah untuk diketahui.)
DocMax

@ DocMax: Meninggalkan ekspresi diperluas memiliki hasil yang sama (497y / 400 harus sama: y / 100 dikurangi dan y / 400 ditambahkan lagi terlepas). Saya menduga bahwa PHP hanya memotong semua setelah desimal daripada membulatkannya. Saya menguji ini dengan pembulatan sebelum modulo. Ini memperbaiki dua anomali, tetapi 19040229 masih mengembalikan hasil yang sama. Ada ide lain?
rintaun

@ rintaun saya tidak berpikir itu pembulatan. Mereka secara fundamental berbeda. Ambil contoh dari atas (y = 4): 497 * 4/400 = 1988/400 = 4 tetapi di sisi lain 4 + 4 / 4-4 / 100 + 4/400 = 4 + 1-0 + 0 = 5 . Persyaratan / 100 dan / 400 mendapatkan terlalu banyak berat dalam perhitungan Anda sehingga 2000 tidak dapat dijangkau.
Howard

2

C - 129

main(y,m,d,s)
{
    scanf("%04d%02d%02d",&y,&m,&d);
    y-=s=86400;
    d+=y+"-addgbegcfadf"[m];
    m>2?y++:0;
    putchar(48+(d+y/4-y/100+y/400+s+s)%7);
}

Ini menyalahgunakan bagaimana pembagian berputar ke nol, setidaknya pada sistem saya (Linux x86).

Konstanta ajaib 86400,, melayani dua tujuan:

  • Kurangi dari tahun untuk membuatnya negatif, tanpa memengaruhi hari dalam seminggu. Ini membuatnya sehingga divisi akan mengumpulkan bukan ke bawah.
  • Geser nomor hari sehingga Senin akan menjadi 0.

Itu juga merupakan jumlah detik dalam sehari.


Gunakan y+=m>2;alih-alih m>2?y++:0;dan cukur beberapa byte.
jelas

2

Javascript, 126 123 karakter

Menggunakan algoritma Sakamoto dengan 0 = Minggu:

prompt().replace(/(....)(..)(..)/,function(_,y,m,d){y-=m<3;alert((+d+y-~(y/4)+~(y/100)-~(y/400)+ +".621462403513"[+m])%7)})

Saya curiga divisi-divisi itu bisa runtuh, tetapi saat ini saya tidak melihatnya.

Sunting: Memperbaiki divisi (tidak perlu ~~ketika Anda bisa saja ~).


2

Python 2 , 83 116 113 109 byte

Menerapkan algoritma Sakamoto . Saran bermain golf diterima. Cobalah online!

Sunting: Saya harus memperbaikinya beberapa waktu yang lalu. -6 byte dari saran Jonathan Allan +2 byte untuk benar-benar memperbaiki kode.

def w(s):m=int(s[4:6]);y,d=int(s[:4])-(m<3),int(s[6:]);return(y+y/4-y/100+y/400+int('032503514624'[m-1])+d)%7

Input harus berupa string tunggal.
msh210

int('032503514624'[m-1])hemat 6
Jonathan Allan

0

Perl - 110 byte

Berikut ini adalah solusi untuk dijalankan dengan perl -p source.pl ATAU perl -pe 'di sini adalah kode'.

s/((..)(..))(..)(..)/(1+3*$1+$2-2*($1%4+$2%4)-(2<$4?$4+(1&$4&&4-(8&$4)):(2^$4)+(!($3%4)-!-$3+!($2%4)))+$5)%7/e

Cukup salin-tempel kasus uji ke stdin.

Ini tampaknya menjadi satu-satunya kode tanpa variabel, konstanta string, dan divisi.


0

JavaScript (ES6), 73 byte (Tidak bersaing)

d=>(w=new Date(d[s="slice"](0,4),d[s](4,6)-1,d[s](-2)).getDay())-(w?1:-6)

Cobalah

f=
d=>(w=new Date(d[s="slice"](0,4),d[s](4,6)-1,d[s](-2)).getDay())-(w?1:-6)
o.innerText=f(i.value="59161021")
oninput=_=>i.value.length==8&&(o.innerText=f(i.value))
<input id=i type=number><pre id=o>


Kenapa tidak bersaing?
programmer5000

@ programmer5000, periksa tanggal tantangan itu diposting;)
Shaggy
Dengan menggunakan situs kami, Anda mengakui telah membaca dan memahami Kebijakan Cookie dan Kebijakan Privasi kami.
Licensed under cc by-sa 3.0 with attribution required.