Holen Sie sich das Datum des n-ten Wochentags in einem bestimmten Jahr und Monat

17

Einführung

Häufig werden Daten als "zweiter Freitag im August 2018" oder "vierter Sonntag im März 2012" bezeichnet. Aber es ist schwer zu sagen, welches Datum das ist! Ihre Aufgabe besteht darin, ein Programm zu schreiben, das ein Jahr, einen Monat, einen Wochentag und eine Ganzzahl empfängt, und dieses Datum auszugeben.

Herausforderung

  • Als Eingabe erhalten Sie ein Jahr, einen Monat, einen Wochentag und eine Zahl.

  • Sie können Eingaben in jedem vernünftigen Format vornehmen, z. B. unter Verwendung einer Zeichenfolge für den Wochentag oder unter Verwendung eines mit Null indizierten Wochentags, oder sogar das Jahr und den Monat in einer einzelnen Zeichenfolge. Erläutern Sie jedoch Ihr Eingabeformat in Ihrer Antwort.

  • Die Ganzzahl, die angibt, an welchem ​​Wochentag im Monat das Ziel festgelegt werden soll, ist eine Ganzzahl von 1-5. Die Ganzzahl bezieht sich niemals auf einen Wochentag, der nicht existiert (z. B. den fünften Freitag im Februar 2019, der nicht existiert).

  • Jahre werden immer positiv sein.

  • Ihre Ausgabe kann in jedem vernünftigen Format erfolgen, einschließlich des Ausdrucks Ihres Enddatums. Bitte erläutern Sie jedoch Ihr Ausgabeformat und Ihre Antwort.

  • Die Angabe von Jahr und Monat in der Ausgabe ist optional. Sie können auch davon ausgehen, dass das Datum gültig ist.

Beispiel für Ein- und Ausgabe

Betrachten Sie diese Eingabe, wobei das Format das Jahr als 4-stellige Zahl, den Monat als Ganzzahl, den Wochentag als Zeichenfolge und die Ordnungszahl als Ganzzahl verwendet:

2019, 3, Samstag, 2
2019, 12, Sonntag, 1
2019, 9 Samstag, 1

Ausgabe:

9. März, 1.
Dezember,
7. September

Das ist , also gewinnt die kürzeste Antwort.

Verkörperung der Ignoranz
quelle
1
Ich dachte, ich könnte GNU verwenden date, aber amüsanterweise hat der Parser hier eine interessante Interpretation .
Türklinke
Darf die Wochennummer 0-indiziert sein?
Jo King
Sicher, wenn es zu Ihrem Programm passt
Verkörperung der Ignoranz
Empfohlene Testfall: 2018, 12, Sonntag 1
Adám
Vorgeschlagener Testfall: der erste Samstag im September 2019
Shaggy

Antworten:

4

MediaWiki-Vorlage, 19 Bytes

{{#time:r|{{{1}}}}}

Dies ist ein MediaWiki Template ParserFunctions Port dieser PHP Antwort

Hinweis: #timeVerwenden Sie PHP strtotimeintern.


Sample Input

{{#time: r | zweiter Samstag im März 2019}}

Beispielausgabe

Sa, 09. März 2019 00:00:00 +0000

tsh
quelle
3

Japt, 19 15 Bytes

Eingabe ist: Jahr, 0-basierter Index des Monats, 0-basierter Index des Wochentags ( 0ist Sonntag) & n.

_XµW¶Ze}f@ÐUVYÄ

Versuch es

                    :Implicit input of U=year, V=month, W=weekday & X=n
       }f           :Output the first element generated by the right function that returns
                    : falsey (0) when passed through the left function
         @          :Right function. Y=0-based index of current iteration
          ÐUVYÄ     :  new Date(U,V,Y+1)
_                   :Left function. Z=date being passed
 Xµ                 :  Decrement X by
   W¶               :   Test W for equality with
     Ze             :    Z.getDay()
Zottelig
quelle
2

C # (Visual C # Interactive Compiler) , 59 Byte

(y,m,d,w)=>1+(d-(int)new DateTime(y,m,1).DayOfWeek+7)%7+7*w

Probieren Sie es online!

-27 Bytes dank @EmbodimentOfIgnorance!

Weniger Golf Code ...

// y: year
// m: month
// d: day of week (0 is Sunday)
// w: week number (0 based)
(y,m,d,w)=>
  // start on the first day of the month
  1+
  // determine the number of days to
  // the first occurrence of the
  // requested weekday
  (d-(int)new DateTime(y,m,1).DayOfWeek+7)%7+
  // add the number of requested weeks
  7*w

Der Rückgabewert ist eine Ganzzahl für den Tag des Monats des angeforderten Datums.

Dana
quelle
Wenn Sie nur den Tag des Monats zurückgeben, der erlaubt ist, können Sie dies auf 59 Bytes
reduzieren
Nochmals vielen Dank für den Tipp - (das ist heute 2x;) Ich werde meine Antworten aktualisieren.
Dana
2

SmileBASIC, 58 51 48 46 45 Bytes

READ N,M$DTREAD M$OUT,,D,W?(5-W+D*2)MOD 7+N*7

Die Eingabe erfolgt in der Form: week,year/month/weekday

  • week: Wochennummer, 0-indiziert
  • year: Jahr, 4 Stellen
  • month: Monat (1-indiziert), 2-stellig 0aufgefüllt
  • weekday: Wochentag (1-indiziert, 1 = Sonntag), 2-stellig 0aufgefüllt

Ausgabe ist der Tag des Monats, 0 indiziert.
Der 2. Samstag im März 2019 wäre 1,2019/03/078(9. März)

Ungolfed

READ WEEK,M$
DTREAD M$ OUT ,,D,W
'Functions in SB can output multiple values using OUT.
'In this case, we don't need the first 2 values, so no variables are given.

PRINT (5-W+ D*2) MOD 7 +WEEK*7

Erläuterung

Das Eingabeformular wurde speziell ausgewählt, damit das Jahr / Monat / Wochentag direkt übergeben werden kann. DTREADDies ist eine Funktion, die eine YYYY/MM/DDZeichenfolge analysiert und das Jahr / Monat / Tag als Zahlen zurückgibt sowie den Wochentag berechnet.

Beachten Sie jedoch, dass DTREADwir den Wochentag angeben, an dem der Tag des Monats erwartet wird. Dies macht die Sache komplizierter, bedeutet aber auch, dass weniger Eingabewerte vorhanden sind und /01das Ende der Datumszeichenfolge nicht ergänzt werden muss .

DTREADAusgänge Wund D.
Wist der Wochentag und der Wochentag Ddes Wdritten Tages des Monats.
(Wenn Sie also 7als Wochentag eingeben, Dwird 7und Wwird dies der Wochentag sein, an dem der 7. Tag des Monats liegt.)

Der Ausdruck (5-W+D*2)MOD 7wird verwendet, um das erste Vorkommen des eingegebenen Wochentags als 0-indizierten Tag des Monats abzurufen. (Ich habe dies hauptsächlich durch Ausprobieren herausgefunden.)

Danach fügt das Programm nur noch hinzu WEEK*7.


Ich wünschte wirklich, es gäbe getrennte Wörter für "Tag der Woche" und "Tag des Monats".

12Me21
quelle
2

Perl 6 , 52 48 Bytes

{1+($^c+4-Date.new($^a,$^b,1).daycount)%7+$^d*7}

Probieren Sie es online!

Anonymer Codeblock, der als Jahr, Monat, Wochentag (Sonntag ist 0) und Wochennummer (0 indiziert) eingegeben wird. Die Ausgabe ist ein Datumsobjekt.

Alte Erklärung:

{                                                  } # Anonymous code block
 (   Date.new(         ))   # Create a new date with
              $^a,$^b,1     # With year, month and the first day
  $_=                       # Save in the variable $_
                         +  # Add to this
                           $^c+4                     # The given day plus 4
                          (     -.daycount)          # The number of days since 17 Nov, 1858
                                           %7        # Modulo 7 to get the correct day
                                             +$^d*7  # Plus the 7 times the number of weeks
Scherzen
quelle
Ich denke, die
Wochennummer
@ 12Me21 Die Frage besagt, dass die Eingabe flexibel ist, aber ich habe gefragt, ob wir eine Take-Week-Nummer als 0 indiziert haben
Jo King
Dies scheint für andere Monate nicht zu funktionieren. Ich denke du brauchst $^c+4-$!.daycount.
Nwellnhof
@nwellnhof Ah, ich hätte darüber nachdenken sollen, anstatt Versuch und Irrtum, lol. Sollte jetzt behoben sein
Jo King
1

MATL , 28 27 Bytes

'1 'ihYO31:q+t8XOi=!A)i)1XO

Dies verwendet drei Eingänge:

  • Zeichenfolge mit Monat und Jahr: 'March 2019'
  • Zeichenfolge mit drei Buchstaben in Großbuchstaben, die den Wochentag angibt: ' Sat'
  • Nummer: 2.

Die Ausgabe ist eine Zeichenkette mit Tag, Monat und Jahr mit Bindestrichen getrennt: 09-Mar-2019.

Probieren Sie es online!

Erläuterung

Betrachten Sie Eingänge 'March 2019', 'Sat', 2.

'1 '    % Push this string
        % STACK: '1 '
ih      % Input string: month and year. Concatenate
        % STACK: '1 March 2019'
YO      % Convert to serial date number
        % STACK: 737485
31:q+   % Create vector [0 1 2 ... 30] and add element-wise
        % STACK: [737485 737486 737487 ... 737515]
t8XO    % Duplicate. Convert to date format 'ddd': day of week in three letters. Gives
        % a 2D char array
        % STACK: [737485 737486 737487 ... 737515], ['Fri'; 'Sat'; 'Sun'; ...; 'Sun']
i=      % Input string: day of week in three letters. Compare element-wise with broadcast
        % STACK: [737485 737486 737487 ... 737515],
        % [0 0 0; 0 0 0; ...; 1 1 1; 0 0 0; ... 1 1 1; ...]
!A      % True for rows containing only 1
        % STACK: [737485 737486 737487 ... 737515], [0 0 ... 1 ... 0 ... 1 ...]
)       % Index: uses the second vector as a mask into the first
        % STACK: [737486 737493 737500 737507 737514]
i)      % Input number. Index
        % STACK: 737493
1XO     % Convert to date format 'dd-mmm-yyyy'. Implicit display
        % STACK: '09-Mar-2019'
Luis Mendo
quelle
1

Python 3 , 92 82 Bytes

82 Bytes dank @Jo King

lambda y,m,d,w:z(y,m)[w-(z(y,m)[0][d]>0)][d]
from calendar import*
z=monthcalendar

Probieren Sie es online!

Originalversion, 92 Bytes

from calendar import*
def f(y,m,d,w):
 x=monthcalendar(y,m)
 if x[0][d]:w-=1
 return x[w][d]

Probieren Sie es online!

Nimmt das Jahr als Ganzzahl, den Monat als 1-indexierte Ganzzahl, den Wochentag als 0-indexierte Ganzzahl, wobei Montag 0und Sonntag sind 6, und die Woche des Monats als 1-indexierte Ganzzahl.

Wie es funktioniert:

# import monthcalendar
from calendar import*
# function with 4 inputs
def f(y,m,d,w):
 # get a 2-D array representing the specified month
 # each week is represented by an array
 # and the value of each element is its date of the month
 # Monday is the 0th element of each week, Sunday is the 6th element
 # days of the first week of the month before the 1st are 0s 
 x=monthcalendar(y,m)
 # if the first week of the month includes the desired day of week
 # convert the week of month to 0-index so that it takes into account the first week
 if x[0][d]:w-=1
 # return the weekday of the week number specified
 return x[w][d]
Neil A.
quelle
1

R , 72 69 Bytes

function(y,m,d,n,D=as.Date(paste0(y,-m,-1))+0:31)D[weekdays(D)==d][n]

Probieren Sie es online!

Eingaben nehmen als:

  • Jahreszahl
  • Monatszahl (1-12)
  • Wochentagsstring im aktuellen Gebietsschema (TIO erfordert englischen Namen mit Großbuchstaben)
  • Ordnungszahl (1-indiziert)
digEmAll
quelle
0

PHP , 46 , 43 , 31 Bytes

<?=date(d,strtotime($argv[1]));

Probieren Sie es online!

Das Programm erhält als Eingabe einen String wie "second saturday of March 2019"

Das Programm druckt die Tageszahl.

-12 Bytes dank Shaggy.

Кирилл Малышев
quelle
1
31 Bytes
Shaggy
Ich glaube auch nicht, dass du das ofin der Eingabe brauchst .
Shaggy
@ Shaggy, ich denke das sind Details. Es kann viele Möglichkeiten geben.
Кирилл Малышев
0

Groovy , 46 Bytes

{y,m,d,w->r=new Date(y,m,7*w)
r-(r.day+7-d)%7}

Probieren Sie es online!

Eingabe als Jahre seit 1900, 0-indizierter Monat, 0-indizierter Tag (Sonntag ist 0) und Wochennummer

Nur ASCII
quelle
0

Rot , 64 60 Bytes

func[y m d n][a: to-date[1 m y]d - a/10 - 7 % 7 +(n * 7)+ a]

Probieren Sie es online!

Nimmt das Jahr, den Monat und den Wochentag als Zahlen, 1-indiziert, Montag ist der erste Tag der Woche.

Galen Ivanov
quelle
huh, to-dateist eine sache. Vielleicht wäre dies in der Weihnachtsabend-Format-Herausforderung nützlich
ASCII-
@ Nur ASCII Wir haben nowfür diese Herausforderung verwendet
Galen Ivanov
1
Ja, aber ich dachte an alternative Methoden (nämlich die <repeat " Eve"date2-date1 times> -Methode iirc)
ASCII
@ Nur ASCII>> 25-Dec-2019 - 1-1-2019 == 358
Galen Ivanov
0

APL (Dyalog Unicode) , 36 Byte SBCS

Volles Programm. Eingabeaufforderungen für [year,month](Januar ist 1), dann für Tag (Sonntag ist 0), dann für n (zuerst ist 1).

date⎕⊃d/⍨⎕=7|d←(⍳31)+days⎕⊣⎕CY'dfns'

Probieren Sie es online!

⎕CY'dfns'c o p y in der dfns- bibliothek

 verwerfe das Ergebnis zugunsten von ...

 Eingabeaufforderung für [year,month]Zahlen

days[c]  Tage [n] seit 1899.12.31 des 0 - ten des Monats

(⍳31)+ addieren sich die i ntegers 1 ... 31 , dass

d← store in d(für d ay Zahlen)

7| Divisionsrest bei Division durch 7 (Wochentag, wobei Sonntag aufgrund einer guten Epoche 0 ist)

⎕= Eingabeaufforderung zur Eingabe der Wochentagsnummer und zum Abrufen einer Maske, bei der die Wochentagsnummern gleich sind

d/⍨ Filter dmit dieser Maske

⎕⊃ Eingabeaufforderung Konsole für n und verwenden Sie diese, um aus der Liste der Tagesnummern auszuwählen

date[c]  datetime stamp [n] (hat nachgestellte Nullen für Stunden, Minuten, Sekunden, Millisekunden)


Klicken Sie für Code auf [c] und für Notizen auf [n] .

Adam
quelle
0

JavaScript (ES6), 49 48 Bytes

f=
(a,d,n)=>(d+6-new Date(...a,7).getDay())%7+n*7-6
<div oninput=o.textContent=f([+y.value,+m.value],+d.value,+n.value)>Year: <input id=y type=number value=2019><br>Month: <select id=m><option value=0>Jan<option value=1>Feb<option value=2>Mar<option value=3>Apr<option value=4>May<option value=5>Jun<option value=6>Jul<option value=7>Aug<option value=8>Sep<option value=9>Oct<option value=10>Nov<option value=11>Dec</select><br>Day: <select id=d><option value=0>Sun<option value=1>Mon<option value=2>Tue<option value=3>Wed<option value=4>Thu<option value=5>Fri<option value=6>Sat</select><br>Count: <input id=n type=number value=1 min=1 max=5><pre id=o>

Übernimmt Parameter als f([year, month], day, number). Monat und Wochentag (ab Sonntag) werden mit Nullen indiziert. Bearbeiten: 1 Byte dank @Shaggy gespeichert.

Neil
quelle
Liegt der Wochentag im Format Sonntag-Samstag oder Montag-Sonntag?
Verkörperung der Ignoranz
@EmbodimentofIgnorance Entschuldigung, ich wusste, dass ich etwas vergessen hatte. (Das Snippet verwendet jetzt Select, um es einfacher zu machen.)
Neil,
@EmbodimentofIgnorance, Sonntag ist 0 in JS.
Shaggy
Oh. Ich wusste das nicht, ich kenne mich mit Javascript nicht so gut aus.
Verkörperung der Ignoranz
48 Bytes
Shaggy
0

TSQL, 106 Bytes

DECLARE @ datetime='2019',@m int=3,@w char(2)='saturday',@p int=2

SELECT dateadd(wk,datediff(d,x,dateadd(m,@m-1,@)-1)/7,x)+@p*7FROM(SELECT
charindex(@w,' tuwethfrsasu')/2x)x

Ausgabe:

2019-03-09 00:00:00.000

Versuch es

t-clausen.dk
quelle
0

Kotlin , 131 84 Bytes

47 Bytes dank nur ASCII-Code und Kommentar.

Eingabe: Jahr, Monat, Wochentag, Woche

Alle ganzen Zahlen von 1 bis maximal in einer einzelnen Zeile. Die Wochentagsnummer ist Sonntag von 1 bis Samstag von 7. Das Hauptprogramm lässt das Jahr 1900 für Datumsklasse verlieren und Monat und Wochentag werden so verschoben, dass sie mit Null anstelle von Eins beginnen, bevor das Lambda aufgerufen wird. Sie können Ihre Argumente in das Eingabetextfeld eingeben, um Ihre eigenen Daten zu testen.

Ausgabe: eine Datumsklasseninstanz. Das Hauptprogramm zeigt das Ergebnis wie folgt an: Sat Mar 09 00:00:00 UTC 2019.

Es gibt eine erweiterte Version mit Kommentaren, die den Code für diejenigen erklären, die mehr erfahren möchten.

{y,m,d,w->val r=java.util.Date(y,m,7*w)
r.setDate(r.getDate()-(r.getDay()+7-d)%7)
r}

Probieren Sie es online!

JohnWells
quelle
1
74 - Verwendet dieselbe Methode wie Scala- und Groovy-Antworten
Nur ASCII
1
Behoben, 84
Nur ASCII
1
Der Importbefehl ist nicht mehr erforderlich, das ist also kein Problem: P
Nur ASCII