Calcola il numero del giorno dell'anno


13

Sembra che non ne abbiamo ancora uno, quindi eccoci qui:

La sfida

Scrivi un programma o una funzione che accetta una data come input e genera il numero del giorno dell'anno. Non puoi usare alcun builtin per quello!

Regole

  • Come al solito puoi scrivere un programma completo o una funzione.
  • Il formato dell'input dipende da te, ma deve contenere un anno, un mese e un giorno. Chiarisci quale utilizza la tua soluzione!
  • Non sono ammessi builtin relativi alla data! Devi fare il lavoro da solo. I builtin che non sono correlati alle operazioni sulla data vanno bene.
  • La base per il calcolo è il calendario gregoriano.
  • Devi tener conto degli anni bisestili.
  • Hai solo bisogno di gestire anni nella gamma [1, 9999]
  • Sono vietate le scappatoie standard .
  • Vince il conteggio dei byte più basso!

Casi test

Il formato di input qui è AAAA / MM / GG

2016/07/05 -> 187
2000/03/28 -> 88
0666/06/06 -> 157
6789/10/11 -> 284
0004/04/04 -> 95
1337/07/13 -> 194

Buona programmazione!


Possiamo usare i built-in per giorni da una certa data? Che dire se un anno è un anno bisestile?
lirtosiast,

@Thomas Non sono ammessi builtin relativi alla data. Lo chiarirò nella sfida, grazie per il commento! :)
Denker,

@DenkerAffe Perché hai proibito tutti i built-in?
aloisdg si trasferisce su codidact.com il

Risposte:


2

Pyth, 31 byte

+s<X1+L28jC"3Ȕ"4!%|F_jQ*TT4tEE

Grazie a @Dennis e @Jakube per la parte dell'anno bisestile . L'input è AAAA, MM, GG su righe separate.

+                          add [day] to
  s <                      sum of first [month]-1 values in the list
      X                    add 1 to
        1                  the second element (January)...
        +L                 \
           28              |
           j               }   lengths of all the months
             C "3Ȕ"       | 
             4             /
        ! %                ... if the year is a leap year; that is, 4 divides...
            |F _ j         fold logical OR over reversed
                   Q       the year
                   *TT     converted to base 100
            4
      t E                 [month]-1
  E                       [day]

Suite di test .


8

JavaScript ES6, 81 69 byte

(y,m,d)=>d+parseInt("03479cehkmpr"[--m],36)+m*28-(y%(y%25?4:16)&&m>1)

Supponendo che i mesi siano basati su 1, altrimenti potrei risparmiare 2 byte.

Modifica: salvato 12 byte usando il suggerimento di @ user81655.


3

C, 96 102 89 61 byte

g(y,m,d){printf("%d",m/2*31+--m/2*30-(y%(y%25?4:16)?2:1)+d);}

2

Python 3, 152 148 150 byte

m,d,y=map(int,input().split());n=[0,31,(59,60)[(y%4==0 and y%100!=0)or y%400==0]]
for i in range(m):n+=[n[-1]+(31,30)[i in[1,3,6,8]]]
print(n[-4]+d)

Prende le date nel formato "MD AAAA".


1
Dovresti usare Python 2, a meno che tu non abbia bisogno di funzionalità specifiche da Python 3. Perché allora non hai bisogno di parentesi nelle tue stampe che ti consenta di salvare un byte contorcendo la tua stampa comeprint n[m-1]+d
Denker

Nella prima riga, potresti scrivere y% 4 == 0e y% 100! = 0, credo
Mega Man

2

Python 2, 100 82 byte

Una porta Python della risposta di @ Neil :

lambda d,m,y:d+int("03479cehkmpr"[m-1],36)+(m-1)*28-(y%(4if y%25 else 16)and m>2)

Come per la risposta precedente, l'aggiunta di 17 byte (99 byte in totale) produrrà un programma completo:

print(lambda d,m,y:d+int("03479cehkmpr"[m-1],36)+(m-1)*28-(y%(4if y%25 else 16)and m>2))(*input())

Risposta precedente:

Come un lambda anonimo:

lambda d,m,y:d+sum(31-(n in(3,5,8,10))for n in range(m-1))-(3if y%4 or(y%400!=0and y%100==0)else 2)

Può essere convertito in un lambda denominato per una penalità di 2 byte. In alternativa, è possibile ottenere un programma completo (prendendo input nel formato D,M,Y) per 117 byte:

print(lambda d,m,y:d+sum(31-(n in(3,5,8,10))for n in range(m-1))-(3if y%4 or(y%400!=0and y%100==0)else 2))(*input())

Alcuni piccoli campi da golf ottengono 76 byte
Ripristina Monica il

0

Python 3, 125 byte

print((lambda d,m,y:sum([3,not(y%400 and not y%100 or y%4),3,2,3,2,3,3,2,3,2,3][:m-1])+m*28-28+d)(*map(int,input().split())))

Un altro approccio a questo problema. Il codice sfrutta le priorità di esecuzione dell'algebra booleana di Python e poiché notè l'ultima operazione, la conversione in booleana è automatica. Al termine della somma, il valore booleano viene trattato come 1 o 0. Il formato di input è la stringa "AA MM GGGG". Sistema di input ispirato a quello simile di @ SteveEckert .

Un'altra forma come funzione, 91 byte

def f(d,m,y):return sum([3,not(y%400 and not y%100 or y%4),3,2,3,2,3,3,2,3,2,3][:m])+m*28+d

In questo caso, l'input è di tre numeri interi, il mese compreso tra 0 e 11. Funzionerebbe anche in Python 2.


0

Excel, 106 byte

=AND(C1>2,OR(MOD(A1,400)=0,AND(MOD(A1,4)=0,MOD(A1,100))))+30*B1-31+CHOOSE(B1,1,2,0,1,1,2,2,3,4,4,5,5,6)+C1

Accetta input in tre celle A1= Anno, B1= Mese, C1= Giorno.


AND(C1>2,OR(MOD(A1,400)=0,AND(MOD(A1,4)=0,MOD(A1,100))))

1 se LeapYear, altro 0

30*B1-31+CHOOSE(B1,1,2,0,1,1,2,2,3,4,4,5,5,6)+C1

Multiplo di 30, SCEGLI per giorni aggiuntivi, più giorni al mese


Evoluzione:

=IF(AND(C1>2,OR(MOD(A1,400)=0,AND(MOD(A1,4)=0,MOD(A1,100)))),1,0)+CHOOSE(B1,0,31,59,90,120,151,181,212,243,273,304,334,365)+C1
=IF(AND(C1>2,OR(MOD(A1,400)=0,AND(MOD(A1,4)=0,MOD(A1,100)))),1,0)+CHOOSE(B1-1,31,59,90,120,151,181,212,243,273,304,334,365)+C1
=IF(AND(C1>2,OR(MOD(A1,400)=0,AND(MOD(A1,4)=0,MOD(A1,100)))),1,0)+30*(B1-1)+CHOOSE(B1,0,1,-1,0,0,1,1,2,3,3,4,4,5)+C1
=IF(AND(C1>2,OR(MOD(A1,400)=0,AND(MOD(A1,4)=0,MOD(A1,100)))),1,0)+30*B1-30+CHOOSE(B1,0,1,-1,0,0,1,1,2,3,3,4,4,5)+C1
=IF(AND(C1>2,OR(MOD(A1,400)=0,AND(MOD(A1,4)=0,MOD(A1,100)))),1,0)+30*B1-31+CHOOSE(B1,1,2,0,1,1,2,2,3,4,4,5,5,6)+C1
=AND(C1>2,OR(MOD(A1,400)=0,AND(MOD(A1,4)=0,MOD(A1,100))))+30*B1-31+CHOOSE(B1,1,2,0,1,1,2,2,3,4,4,5,5,6)+C1
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.