Ini tugas tahunan, oke


22

Diberi angka 1≤n≤365, menampilkan hari ke-n tahun dalam format "Hari-angka Bulan". Misalnya, mengingat 1, Anda harus menampilkan "1 Januari", tanpa "dari".

Kalender Gregorian akan digunakan dan program seharusnya tidak menghitung tahun kabisat, jadi program Anda seharusnya tidak menghasilkan "29 Februari" dalam keadaan apa pun. Metode apa pun dapat digunakan, asalkan mengikuti format "Bulan-angka Bulan" yang disebutkan sebelumnya. Program Anda juga harus mengeluarkan tata cara dengan benar, artinya harus selalu menampilkan 1, 2, 3, masing-masing harus 1, 2 atau 3 menjadi angka hari untuk setiap input. Ruang terkemuka atau lekukan lain diizinkan.

Ini kode golf, jadi solusi terpendek berdasarkan karakter menang.

Kasus uji:

1 gives 1st January
2 gives 2nd January
3 gives 3rd January
365 gives 31st December
60 gives 1st March
11 gives 11th January

4
Juga, apakah Anda perlu memaksa pesan kesalahan pada angka> 365? Bisakah program mengasumsikan bahwa input tidak valid dan tidak perlu mengatasinya?
Rɪᴋᴇʀ

5
Karena tidak semua orang adalah penutur asli bahasa Inggris, Anda mungkin ingin menambahkan bahwa hari nomor 11, 12, dan 13 mendapatkan "th", angka yang berakhiran "1" get "st", "2" get "nd", "3" dapatkan "rd", dan yang lainnya mendapatkan "th".
Adam

9
Wah, jangan terima jawaban dengan begitu cepat. Terutama jawaban yang tidak salah !
Adam

6
Anda harus menambahkan setidaknya 11(11 th Januari) dan 21(21 st Januari) untuk uji kasus.
Arnauld

1
Dan saat Anda mengedit kotak uji, mungkin tentukan apa sebenarnya format kotak uji Anda. Beberapa penjawab berpikir itu 123=adalah bagian dari output yang diperlukan. Atau cukup edit kotak uji untuk membaca sesuatu seperti: 365beri31st December
Adam

Jawaban:


9

PHP ,38 40 30 28 byte

<?=date("jS F",86399*$argn);

Cobalah online!

Jalankan dengan php -nFinput dari STDIN. Contoh (skrip di atas bernama y.php):

$ echo 1|php -nF y.php
1st January
$ echo 2| php -nF y.php
2nd January
$ echo 3| php -nF y.php
3rd January
$ echo 11|php -nF y.php
11th January
$ echo 21|php -nF y.php
21st January
$ echo 60|php -nF y.php
1st March
$ echo 365|php -nF y.php
31st December

Penjelasan

Bangun cap waktu zaman untuk hari yang diinginkan pada tahun 1970 (mudah bukan tahun kabisat) dengan mengalikan day number * number of seconds per day(86400). Namun, ini akan menghasilkan satu hari lebih tinggi sehingga gandakan dengan number of seconds in a day - 1(86399) yang untuk rentang nomor input (1≤n≤365) akan dihasilkan dengan cap waktu akhir setiap hari yang benar. Kemudian gunakan saja format tanggal bawaan PHP untuk output.


mengapa itu -nperlu?
Ven

@Ven itu mungkin tidak dalam semua kasus, tetapi hanya menonaktifkan pengaturan di php.ini lokal yang mungkin membuat perilaku tidak konsisten.
640KB

6

Jelly ,  79 78  77 byte

-1 memperbaiki bug :) (tidak harus melakukan pra-transposisi untuk menemukan indeks, harus melakukan post-reverse, tetapi kemudian kita dapat mengekor alih-alih kepala)
-1 menggunakan refleksi ( ⁽©ṅB+30_2¦2-> ⁽0ṗb4+28m0)

⁽0ṗb4+28m0SRṁRƲœiµṪȮ%30%20«4ị“nḄƲf⁷»s3¤Ṗ,ị“£ṢtẒ⁽ẹ½MḊxɲȧėAṅ ɓaṾ¥D¹ṀẏD8÷ṬØ»Ḳ¤$K

Program lengkap yang mencetak hasilnya

Cobalah online!

Bagaimana?

akan memperbarui ini nanti ...

⁽©ṅB+30_2¦2SRṁRƲZœiµḢȮ%30%20«4ị“nḄƲf⁷»s3¤Ṗ,ị“...»Ḳ¤$K - Main Link: integer, n
⁽©ṅB+30_2¦2SRṁRƲZœi - f(n) to get list of integers, [day, month]
⁽©ṅ                 - compressed literal 2741
   B                - to a list of binary digits -> [ 1, 0, 1, 0, 1, 0, 1, 1, 0, 1, 0, 1]
    +30             - add thirty                    [31,30,31,30,31,30,31,31,30,31,30,31]
         ¦          - sparse application...
        2           - ...to indices: [2]
       _  2         - ...action: subtract two       [31,28,31,30,31,30,31,31,30,31,30,31]
               Ʋ    - last four links as a monad - i.e. f(x):
           S        -   sum x                       365
            R       -   range                       [1..365]
              R     -   range x (vectorises)        [[1..31],[1..28],...]
             ṁ      -   mould like                  [[1..31],[32..59],...]
                Z   - transpose                     [[1,32,...],[2,33,...],...]
                 œi - 1st multi-dimensional index of n  -> [day, month]

µḢȮ%30%20«4ị“nḄƲf⁷»s3¤Ṗ,ị“...»Ḳ¤$K - given [day, month] format and print
µ                                  - start a new monadic chain - i.e. f(x=[day, month])
 Ḣ                                 - head -- get the day leaving x as [month])
  Ȯ                                - print it (with no newline) and yield it
   %30                             - modulo by thirty
      %20                          - modulo by twenty
         «4                        - minimum of that and four
                     ¤             - nilad followed by link(s) as a nilad:
            “nḄƲf⁷»                -   dictionary words "standard"+" the" = "standard the"
                   s3              -   split into threes = ["sta","nda","rd ","the"]
           ị                       - index into
                      Ṗ            - remove rightmost character
                               ¤   - nilad followed by link(s) as a nilad:
                         “...»     -   dictionary words "January"+" February"+...
                              Ḳ    -   split at spaces = ["January","February",...]
                        ị          - index into (vectorises across [month])
                       ,           - pair                  e.g. ["th", ["February"]]
                                K  - join with spaces           ["th ", "February"]
                                   - print (implicitly smashes)   th February

4
Trik "standar" luar biasa.
Ven

Saya setuju dengan @Ven , trik hebat! Ini juga menyimpan byte dalam jawaban 05AB1E saya dibandingkan dengan string terkompresi "thstndrd"menjadi bagian-bagian dari ukuran 2 ( .•oθ2(w•2ô), jadi terima kasih. :)
Kevin Cruijssen

1
Ini harus menjadi salah satu program Jelly terpanjang yang pernah saya lihat.
JAD

6

C # (Visual C # Interactive Compiler) , 115 113 109 98 byte

g=>$"{f=(g=p.AddDays(g-1)).Day}{"tsnr"[f=f%30%20<4?f%10:0]}{"htdd"[f]} {g:MMMM}";DateTime p;int f;

Terima kasih kepada @someone untuk menghemat 9 byte

Cobalah online!


1
@KevinCruijssen Saya mendapatkan modulos rusak, harus diperbaiki sekarang.
Perwujudan Ketidaktahuan

.code.tio(2,22): error CS0165: Use of unassigned local variable 'p'Tampaknya hal struct tidak berfungsi.
JAD

var g=new DateTime().AddDays(n-1)berfungsi
JAD

@JAD kesalahan pada bagian saya, diperbaiki
Perwujudan Ketidaktahuan


5

Python 3.8 (pra-rilis) , 112 byte

lambda x:str(d:=(t:=gmtime(x*86399)).tm_mday)+'tsnrhtdd'[d%5*(d%30%20<4)::4]+strftime(' %B',t)
from time import*

Cobalah online!

Cukup aneh, saya tidak harus tanda kurung d:=(t:=gmtime(~-x*86400), mungkin karena penerjemah hanya memeriksa jika ada ()karakter di sekitar ekspresi penugasan dan bukan bahwa ekspresi itu sendiri di dalam tanda kurung.

-2 Berkat gwaugh .
-5 Terima kasih kepada xnor .


5

Perl 6 , 166 161 byte

{~(.day~(<th st nd rd>[.day%30%20]||'th'),<January February March April May June July August September October November December>[.month-1])}o*+Date.new(1,1,1)-1

Cobalah online!

Hardcode semua nama bulan, yang menghabiskan sebagian besar ruang. Man, Perl 6 benar-benar membutuhkan formatter tanggal yang tepat.


4

Retas, 115 59 39 byte

$x==>date("jS F",mktime(0,0,0,1,$x));

Karena @gwaugh mendapatkan solusi yang sama dengan saya ketika saya bermain golf, saya memposting ini di Hack :).


Wow, pikiran yang hebat berpikir sama. :) +1 untuk Anda pak!
640KB

@ wow haha, saya tidak tahu saya hanya bisa memiliki program tingkat atas. Saya akan mengedit milik saya untuk membuatnya menjadi level atas juga, dan menemukan cara untuk mendapatkan skor yang lebih baik ;-)
Ven

1
@gwaugh Membuat Hack milikku sebagai gantinya.
Ven

1
Anda mungkin ingin menentukan parameter tahun non-kabisat untuk mktime()panggilan Anda jika tidak maka akan mengembalikan output yang salah jika dijalankan pada tahun kabisat. (harus melakukan jawaban saya).
640KB

4

JavaScript (ES6),  117  113 byte

Disimpan 4 byte berkat @tsh

d=>(n=(d=new Date(1,0,d)).getDate())+([,'st','nd','rd'][n%30%20]||'th')+' '+d.toLocaleString('en',{month:'long'})

Cobalah online!

Berkomentar

d =>                     // d = input day
  ( n =                  //
    ( d =                // convert d to
      new Date(1, 0, d)  //   a Date object for the non leap year 1901
    ).getDate()          // save the corresponding day of month into n
  ) + (                  //
    [, 'st', 'nd', 'rd'] // ordinal suffixes
    [n % 30 % 20]        // map { 1, 2, 3, 21, 22, 23, 31 } to { 'st', 'nd', 'rd' }
    || 'th'              // or use 'th' for everything else
  ) + ' ' +              // append a space
  d.toLocaleString(      // convert d to ...
    'en',                // ... the English ...
    { month: 'long' }    // ... month name
  )                      //

Tanpa tanggal bawaan, 188 byte

f=(d,m=0)=>d>(k=31-(1115212>>m*2&3))?f(d-k,m+1):d+([,'st','nd','rd'][d%30%20]||'th')+' '+`JanuaryFebruaryMarchAprilMayJuneJulyAugustSeptemberOctoberNovemberDecember`.match(/.[a-z]*/g)[m]

Cobalah online!


Gagal untuk tanggal 11, 12, 13 setiap bulan
Data Kedaluwarsa

1
@ExpiredData Terima kasih telah melaporkan ini. Diperbaiki sekarang
Arnauld

Abaikan komentar saya, saya membuat kesalahan ID10T.
asgallant

Saya tidak yakin bagaimana nodejs menangani tag bahasa, tetapi tampaknya menggunakan 0akan berfungsi sebagai penggunaan "en". Dan mengubah ke toLocaleStringakan menghemat 4 byte. 110 bytes
tsh

@ tsh Tampaknya toLocaleStringmenggunakan pengaturan default sistem ketika melewati string yang tidak dikenal atau nilai numerik. Jadi, bisa apa saja. Parameter ini pada dasarnya tidak efektif pada instance TIO, karena hanya bahasa Inggris saja yang diinstal .
Arnauld

4

Smalltalk, 126 byte

d:=Date year:1day:n.k:=m:=d dayOfMonth.10<k&(k<14)and:[k:=0].o:={#st.#nd.#rd}at:k\\10ifAbsent:#th.m asString,o,' ',d monthName

1
Saya tidak tahu Smalltalk, tetapi apakah ini benar 11th,12th,13th? Jika saya membaca dengan benar Anda integer-bagi hari dengan 10, tetapi itu berarti itu akan menghasilkan 11st,12nd,13rd, kecuali sesuatu yang lain dalam kode memperbaiki ini sementara saya tidak menyadarinya.
Kevin Cruijssen

@KevinCruijssen Anda benar. Terima kasih telah meminta perhatian saya pada ini. Saya harus menghabiskan beberapa byte lagi untuk memperbaikinya.
Leandro Caniglia

1
@KevinCruijssen, Selesai. Terima kasih lagi.
Leandro Caniglia

3

C # (Visual C # Interactive Compiler) , 141 139 133 124 122 byte

a=>{var d=s.AddDays(a-1);int x=d.Day,m=x%30%20;return x+"thstndrd".Substring(m<4?m*2:0,2)+d.ToString(" MMMM");};DateTime s

Terima kasih kepada Arnauld untuk metode yang lebih cepat untuk menghapus 11,12,13 penghematan 4 byte

Cobalah online!


Menggunakan C # 8, ini dapat direduksi menjadi: a=>{var d=s.AddDays(a-1);int x=d.Day,m=x%30%20;return x+"thstndrd"[(m<4?m*2:0)..2]+$" {d:MMMM}";};DateTime s Kompiler interaktif sepertinya tidak mendukung perubahan level bahasanya menjadi "pratinjau" saat ini.
Arcanox


Saya cukup yakin Anda harus menambahkan titik koma setelahDataTime s
Perwujudan Ketidaktahuan


3

MySQL, 47 45 42 byte

SELECT DATE_FORMAT(MAKEDATE(1,n),"%D %M")

1901 dapat diganti dengan tahun apa pun yang bukan tahun kabisat.

Sunting: menyimpan dua byte dengan menghapus spasi dan tiga byte lainnya dengan mengubah tahun menjadi 1, berkat @Embodyment of Ignorance .


Bisakah Anda menghapus spasi di antara 1901, ndan string?
Perwujudan Ketidaktahuan

@EmbodimentofIgnorance ya saya bisa, terima kasih!
NicolasB

Juga, mengapa tidak mengganti tahun 1901 dengan tahun seperti 1? 1 bukan tahun kabisat, dan ini lebih pendek 3 byte
Perwujudan Ketidaktahuan

@EmbodimentofIgnorance dilakukan dan dilakukan :-)
NicolasB

3

05AB1E , 81 79 78 76 75 74 73 71 70 69 byte

•ΘÏF•ºS₂+.¥-D0›©ÏθDT‰ć≠*4šß„—ÊØ3ôsè¨ð”……‚應…ä†ï€¿…Ë…ê†Ä…æ…Ì…Í”#®OèJ

-9 byte terima kasih kepada @Grimy .
-1 byte berkat standard thetrik @ JonathanAllan untuk th,st,nd,rd, yang ia gunakan dalam jawabannya Jelly .

Cobalah secara online atau verifikasi semua kemungkinan kasus pengujian .

Penjelasan:

•ΘÏF        # Push compressed integer 5254545
     º       # Mirror it vertically: 52545455454525
      S      # Converted to a list of digits: [5,2,5,4,5,4,5,5,4,5,4,5,2,5]
       ₂+    # And 26 to each: [31,28,31,30,31,30,31,31,30,31,30,31,28,31]
             # (the additional trailing 28,31 won't cause any issues)
           # Undelta this list (with automatic leading 0):
             #  [0,31,59,90,120,151,181,212,243,273,304,334,365,393,424]
  -          # Subtract each from the (implicit) input-integer
   D0       # Duplicate the list, and check for each if it's positive (> 0)
      ©      # Store the resulting list in the register (without popping)
       Ï     # Only leave the values at those truthy indices
        θ    # And get the last value from the list, which is our day
D            # Duplicate this day
 T          # Take the divmod-10 of this day: [day//10, day%10]
   ć         # Extract the head; pop and push the remainder-list and head: [day%10], day//10
            # Check whether the day//10 is NOT 1 (0 if day//10 == 1; 1 otherwise)
     *       # Multiply that by the [day%10] value
      4š     # Prepend a 4 to this list
        ß    # Pop and push the minimum of the two (so the result is one of [0,1,2,3,4],
             # where the values are mapped like this: 1..3→1..3; 4..9→4; 10..19→0; 20..23→0..3; 24..29→4; 30,31→0,1)
 thŠØ       # Push dictionary string "th standards"
      3ô     # Split it into parts of size 3: ["th ","sta","nda","rds"]
        sè   # Swap and index the integer into this list (4 wraps around to index 0)
          ¨  # And remove the trailing character from this string
ð            # Push a space " "
”……‚應…ä†ï€¿…Ë…ê†Ä…æ…Ì…Í”
             # Push dictionary string "December January February March April May June July August September October November"
 #           # Split on spaces
  ®          # Push the list of truthy/falsey values from the register again
   O         # Get the amount of truthy values by taking the sum
    è        # Use that to index into the string-list of months (12 wraps around to index 0)
J            # Join everything on the stack together to a single string
             # (and output the result implicitly)

Lihat tip tambang 05AB1E ini untuk memahami alasannya:

  • (bagian Cara menggunakan kamus? ) ”……‚應…ä†ï€¿…Ë…ê†Ä…æ…Ì…Í”adalah"December January February March April May June July August September October November"
  • (bagian Cara menggunakan kamus? ) …thŠØadalah"th standards"
  • (bagian Cara mengompresi bilangan bulat besar? ) •ΘÏF•adalah5254545

1
-2 byte dengan menggunakan 5в28 + untuk kompresi: TIO
Grimmy

1
Menggunakan S adalah ide yang bagus, -1 byte lagi: TIO
Grimmy

1
@Grimy Terima kasih untuk -1 byte untuk •EË7Óæ•S₂+, tapi golf -3 Anda tidak berhasil sayangnya. Pengindeksan secara otomatis membungkus di 05AB1E, jadi itu 5st,6nd,7rd,25st,26nd,27rd,29stakan salah. PS: kalau bisa berhasil, bisa untuk -1 tambahan. :)
Kevin Cruijssen

1
-1 lagi (menggunakan "standar th" bukannya "standar" menghapus kebutuhan untuk Á).
Grimmy

1
-1 ( •C.ñÒā•hingga •ΘÏF•º, digit tambahan tidak masalah)
Grimmy

2

bash, 82 80 byte

-2 byte terima kasih hanya untuk @ ASCII

a=(th st nd rd);set `printf "%(%e %B)T" $[$1*86399]`;echo $1${a[$1%30%20]-th} $2

TIO

bash + tanggal GNU, 77 byte

a=(th st nd rd);set `date -d@$[$1*86399] +%e\ %B`;echo $1${a[$1%30%20]-th} $2


@ Khusus ASCII, ya kurangi 100-an untuk setiap hari, 100 * 365 = 36500-an yang kurang dari satu hari (86400), bekerja juga dengan 86399 (kurangi 1-an setiap hari)
Nahuel Fouilleul

: / masih terlihat sangat panjang tetapi belum menemukan cara yang lebih baik
ASCII-only

2

Shell + coreutils, 112 90 byte

date -d0-12-31\ $1day +%-dth\ %B|sed 's/1th/1st/;s/2th/2nd/;s/3th/3rd/;s/\(1.\).. /\1th /'

Cobalah online! Tautan termasuk kasus uji. Sunting: Disimpan 22 byte berkat @NahuelFouilleul. Penjelasan:

date -d0-12-31\ $1day

Hitung jumlah hari setelah hari pertama sebelum tahun non-kabisat. (Sayangnya Anda tidak dapat melakukan perhitungan tanggal relatif @-1.)

+%-dth\ %B|sed

Keluarkan hari bulan (tanpa memimpin nol) th,, dan nama bulan penuh.

's/1th/1st/;s/2th/2nd/;s/3th/3rd/;

Memperbaiki 1st, 2nd, 3rd, 21st, 22nd, 23rddan 31st.

s/\(1.\).. /\1th /'

Kembalikan 11thke 13th.


saya melihat jawaban ini setelah saya, bisa menghemat 18bytes menggunakan satu perintah sed, juga sdi daysdapat dihapus, dan 19di1969
Nahuel Fouilleul

@NahuelFouilleul Yang terakhir menggunakan Bash-isme jadi harus diposting sebagai jawaban terpisah, tapi terima kasih atas tips lainnya!
Neil

2

Jelly , 115 114 101 97 byte

%30%20¹0<?4Ḥ+ؽị“thstndrd”ṭ
“5<Ḟ’b4+28ÄŻ_@µ>0T,>0$ƇZṪµ1ịị“£ṢtẒ⁽ẹ½MḊxɲȧėAṅ ɓaṾ¥D¹ṀẏD8÷ṬØ»Ḳ¤,2ịÇƊṚK

Cobalah online!

Panjang dengan standar Jelly, tetapi dilakukan dari prinsip pertama.

Terima kasih kepada @JonathanAllan untuk menghemat 13 byte melalui pemahaman yang lebih baik tentang kompresi string.


“£ṢtẒ⁽ẹ½MḊxɲȧėAṅ ɓaṾ¥D¹ṀẏD8÷ṬØ»Ḳ¤akan menghemat 13 (Compress.dictionary mencari ruang terkemuka dan memiliki penanganan khusus untuk itu).
Jonathan Allan

2

Google Sheets, 118 103 86 byte

=day(A1+1)&mid("stndrdth",min(7,1+2*mod(mod(day(A1+1)-1,30),20)),2)&text(A1+1," mmmm")

Saya tidak dapat mengedit komentar saya jadi, inilah versi kode Google Sheets yang berfungsi.

Cobalah secara Online!


1

Merah , 124 byte

func[n][d: 1-1-1 + n - 1[rejoin[d/4 either 5 > t: d/4 % 30 % 20[pick[th st nd rd]t + 1]['th]]pick system/locale/months d/3]]

Cobalah online!

Menambahkan n- 1 hari menjadi 1-1-1 (1-Jan-2001) untuk membentuk tanggal, daripada menggunakan metode Arnauld untuk mengindeks ke akhiran bulan. Sayang sekali Red adalah 1-diindeks, ini membutuhkan tambahan tweaking. Hal yang baik adalah bahwa Red tahu nama-nama bulan ini :)


1

APL (NARS), 235 karakter, 470 byte

{k←↑⍸0<w←+\v←(1-⍵),(12⍴28)+13561787⊤⍨12⍴4⋄k<2:¯1⋄d←1+v[k]-w[k]⋄(⍕d),({d∊11..13:'th'⋄1=10∣d:'st'⋄2=10∣d:'nd'⋄3=10∣d:'rd'⋄'th'}),' ',(k-1)⊃(m≠' ')⊂m←'January February March April May June July August September October November December'}

13561787 adalah angka yang ada di basis 4 dapat dijumlahkan ke (12⍴28) untuk mendapatkan panjang setiap bulan ... tes:

  f←{k←↑⍸0<w←+\v←(1-⍵),(12⍴28)+13561787⊤⍨12⍴4⋄k<2:¯1⋄d←1+v[k]-w[k]⋄(⍕d),({d∊11..13:'th'⋄1=10∣d:'st'⋄2=10∣d:'nd'⋄3=10∣d:'rd'⋄'th'}),' ',(k-1)⊃(m≠' ')⊂m←'January February March April May June July August September October November December'}     
  ⊃f¨1 2 3 365 60 11
1st January  
2nd January  
3rd January  
31st December
1st March    
11th January 

0

C (gcc) , 174 155 byte

i;char a[99],*b="thstndrd";f(long x){x--;x*=86400;strftime(a,98,"%d   %B\0",gmtime(&x));i=*a==49?0:a[1]-48;a[2]=b[i=i>3?0:i*2];a[3]=b[++i];x=*a==48?a+1:a;}

Cobalah online!


-2

Python 3 , 95 Bytes

Mengukur datanya: P

from datetime import *;f=lambda s:(datetime(2019,1,1)+timedelta(days=s-1)).strftime("%d of %B")

Cobalah online!


2
Ini tidak menghasilkan sufiks ordinal, dan memiliki angka nol di awal nomor hari. Itu ofjuga tidak perlu
Jo King
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.