Ihre ganz eigene "für" Anweisung

38

Ihre ganz eigene "für" Anweisung

Angenommen, Sie haben die folgenden Eingaben: a, b, c, d

Die Eingabe kann einzeilig erfolgen, wobei jedes Format ("a / b / c / d" oder "a, b, c, d" usw.) verwendet wird.

Sie können auch 4 Eingänge haben.

Sie müssen das folgende Verhalten codieren (hier Pseudocode):

var i = <a>
while (i <b> <c>)
    print i
    i = i + <d>
    print "\n"

Hier sind einige Testfälle:

input : 1,<,10,1
output :
1
2
3
4
5
6
7
8
9

Einer noch :

input : 20,>,10,1
output :
20
21
22
23
24
25
26
27
...
infinite loop / program crashes
  • aist eine ganze Zahl , der Anfangswert von i.

  • bIst ein String oder ein Zeichen , kann es nicht etwas anderes sein, der Komparator, der in der Endbedingung der forSchleife verwendet wird.

    bkann und muss eine der folgenden Zeichenketten sein:

    - ">"
    - "<"
    
  • cist eine Ganzzahl , die Zahl, die in der Endbedingung der for Schleife verwendet wird.

  • dist eine Ganzzahl , die bei jeder Schleife zu i hinzugefügt wird.

Das ist Code-Golf, die kürzeste Antwort gewinnt!

Sygmei
quelle
1
Können die Nummern von einer Funktion als Liste / Sequenz zurückgegeben werden, anstatt auf stdout gedruckt zu werden?
smls
@smls Nein sorry, die Ausgabe muss den Beispielen entsprechen!
Sygmei
1
Es heißt, mein Code sollte dem Pseudocode folgen und es gibt einen print "\n", aber ich verwende die Javascript-Warnung für jede Zeile. Wäre das akzeptabel oder müsste ich console.log verwenden, um meine Antwort zu verlängern?
2
Sie können die Benachrichtigungsfunktion als Ausgabemethode verwenden, aber Sie können nicht mehrere Benachrichtigungen verwenden. So etwas alert("23\n24\n25");würde funktionieren, während alert("23"); alert("24"); alert(25);nicht
Sygmei

Antworten:

25

JavaScript (ES6),  44  43 56 Bytes

Dank ETHproductions 1 Byte gespart Edit: Korrigiert
, um die Ausgabeanforderungen zu erfüllen

(a,b,c,d)=>{for(s='';eval(a+b+c);a+=d)s+=a+`
`;alert(s)}

Prüfung

Arnauld
quelle
Gute Nutzung des Spielraums!
ETHproductions
Ich denke, Sie können das neu anordnen eval, um ein Byte zu sparen:(a,b,c,d)=>{for(;eval(a+b+c);a+=d)alert(a)}
ETHproductions
@ETHproductions Ah ja. Schön!
Arnauld
5
Das ist eine 44 mit einem Tutu!
am
Dies folgt nicht der Spezifikation, bei der die Ausgabe zeilenweise mit U + 000A nach jeder Zeile erfolgt.
Joey
17

Javascript (ES6), 47 42 48 Bytes

Wollte die for-Version machen, aber jemand war schneller, also hier ist die rekursive Version.

(b,c,d)=>F=a=>eval(a+b+c)&&console.log(a)|F(a+d)

Du musst f=vorher hinzufügen und es so nennen f(b,c,d)(a).

Vielen Dank an Arnauld für das tolle Golfen.

alertgeändert zu console.logaufgrund der Ausgabespezifikation


quelle
@ Arnauld Danke, das ist ein ziemlich cooles Golfspiel. Ich habe ihn nur gefragt, mal sehen, ob er das akzeptiert.
Froh zu sehen, dass es angenommen wurde. ;)
Arnauld
Dies folgt nicht der Spezifikation, bei der die Ausgabe zeilenweise mit U + 000A nach jeder Zeile erfolgt.
Joey
@Joey Das ist nur Pseudocode, aber ich werde OP danach fragen.
@Masterzagh: Es gab bereits eine Frage zu alternativen Ausgabeformaten, die abgelehnt wurde.
Joey
15

Pure Bash, 35

Ich gehe davon aus, dass es in Ordnung ist, nur die Parameter in die Standard-for-Schleife einzufügen:

for((i=$1;i$2$3;i+=$4));{ echo $i;}

Probieren Sie es online aus .

Digitales Trauma
quelle
Haha, bash macht es wirklich einfach
Sygmei
13

Gelee , 12 Bytes

Ṅ+⁶µ⁴;⁵¹vµ¿t

Probieren Sie es online!

Jelly hat viele Möglichkeiten, Iterationen zu wiederholen, Bereiche zu erstellen usw. Das genaue Spiegeln des C ++ - Verhaltens ist jedoch ziemlich schwierig, da Sonderfälle wie das Inkrement 0 sind und die Schleife vor dem Start endet (da die Ungleichung umgekehrt ist) ) und das Inkrement in die falsche Richtung (was bedeutet, dass die Ausgangsbedingung der Schleife nicht auf natürliche Weise erfüllt werden kann). Als solche ist diese Lösung im Grunde genommen eine direkte Übersetzung von C ++, auch wenn sie dadurch weniger umfangreich ist als ein Jelly-Programm normalerweise. Glücklicherweise hat C ++ ein undefiniertes Verhalten beim Überlauf von Ganzzahlen mit Vorzeichen (wird von der Frage verwendet int), was bedeutet, dass ein Programm in diesem Fall alles tun kann und daher nicht versucht werden muss, das Überlaufverhalten nachzuahmen.

Erläuterung

Ṅ+⁶µ⁴;⁵¹vµ¿t
   µ     µ¿   While loop; while ((⁴;⁵¹v) counter) do (counter = (Ṅ+⁶)counter).
    ⁴;⁵       Second input (b) appended to third input (c), e.g. "<10"
        v     Evaluate, e.g. if the counter is 5, "<10" of the counter is true
       ¹      No-op, resolves a parser ambiguity
Ṅ             Output the counter, plus a newline
 +⁶           Add the fourth input (d)
           t  Crashes the program (because the counter is not a list)

Das Programm zum Absturz zu bringen, ist die schnellste Möglichkeit, Jellys implizite Ausgabe zu deaktivieren (andernfalls würde der Endwert des Zählers ausgegeben). es erzeugt eine Reihe von Fehlermeldungen auf stderr, aber wir betrachten dies normalerweise als zulässig.

Im Übrigen wird der Schleifenzähler vor dem Start der Schleife mit dem aktuellen Wert initialisiert. Da die Schleife beim Start des Programms erscheint, ist dies die erste Eingabe.


quelle
Sie könnten ändern t, um keinen Absturz zu haben. Die Löschung führt zu einer leeren Liste, für die Jellys impliziter Ausdruck nichts ergibt.
Jonathan Allan
@JonathanAllan: Tatsächlich ist es nicht so, dass ein Bereich von 2 bis zum angegebenen Wert erstellt wird, der auf einem impliziten Ausdruck definitiv sichtbar ist.
Ah, ich muss diese Theorie mit einer Schleife getestet haben, die im negativen Bereich endet. in der Tat wird implizit ein Bereich erstellt.
Jonathan Allan
Ähm, das sind 12 Zeichen, aber es sind nicht 12 Bytes, oder?
Cruncher
@Cruncher: Jelly verwendet eine eigene Codierung, bei der jedes von der Sprache verwendete Zeichen durch ein einzelnes Byte dargestellt wird (es werden nur 256 verschiedene Zeichen verwendet). Der Grund dafür, dass hier keine besser bekannten Funktionen wie Codepage 437 verwendet werden, liegt darin, dass die Eingabe einfacher ist (ich meine, die Eingabe ist nicht so einfach, aber einfacher als bei einer Sprache wie gs2). Ein Hexdump dieses Programms wäre 12 Bytes lang.
10

R, 63 Bytes

function(a,b,c,d)while(do.call(b,list(a,c))){cat(a,"\n");a=a+d}
Sven Hohenstein
quelle
9

Java, 58 Bytes

(a,b,c,d)->{for(;b>61?a>c:a<c;a+=d)System.out.println(a);}
Roman Gräf
quelle
14
Gibt es einen Grund zu schaffen i? Könnten Sie den Initialisierungsteil überspringen und nur verwenden a? Durch die Verwendung des ASCII-Werts '>' (62) wird auch ein Byte gespeichert.
Riley
6
Nach Rileys Kommentar können Sieb>61
Kritixi Lithos
Ich glaube nicht, dass dies kompiliert.
ChiefTwoPencils
@ChiefTwoPencils Es ist eine Funktion. Sie müssen ein Testprogramm schreiben, um es zu kompilieren.
wizzwizz4
@ wizzwizz4, offensichtlich. Aber das geht immer noch nicht. Versuch es einmal. Außerdem sind nach meinem Verständnis alle zum Ausführen erforderlichen Bytes von Bedeutung.
ChiefTwoPencils
7

05AB1E , 22 20 Bytes

[D²`'>Q"‹›"è.V_#D,³+

Probieren Sie es online!

Erläuterung

[                       # start loop
 D                      # copy top of stack (current value of a)
  ²`                    # push b,c to stack
    '>Q                 # compare b to ">" for equality
       "‹›"             # push this string
           è            # index into the string with this result of the equality check
            .V          # execute this command comparing a with c
              _#        # if the condition is false, exit loop (and program)
                D,      # print a copy of the top of the stack (current value of a)
                  ³+    # increment top of stack (a) by d
Emigna
quelle
1
Jedes Eingabeformat wird akzeptiert, daher ist die zweite Version in Ordnung :)
Sygmei
7

SmileBASIC, 53 Bytes

INPUT A,B$,C,D
S=ASC(B$)-61WHILE S*A>S*C?A
A=A+D
WEND

Erläuterung:

INPUT A,B$,C,D
IF B$=="<" THEN S=-1 ELSE S=1 'get comparison direction
I=A
WHILE S*I>S*C 'loop while I is less than/greater than the end
 PRINT I
 INC I,D
WEND

Dies nutzt die Tatsache, dass X<Ydas gleiche ist wie-X>-Y

12Me21
quelle
Ich vertraue dir für diese, ich habe keine 3DS zu testen :)
Sygmei
Ich habe Petit Computer, so coole Idee! Ich werde irgendwann so etwas versuchen ...
Python-B5
Sie könnten eine READAnweisung verwenden, die 1 Byte spart.
ckjbgames
@ckjbgames wie?
12. Mai,
@ 12Me21 Lesen Sie die SmileBASIC-Handbücher. Es sollte in der Liste der Anweisungen für SmileBASIC enthalten sein.
ckjbgames
6

Gestapelt , 34 Bytes

@d@c@b[show d+][:c b tofunc!]while

Probieren Sie es online! (Testen eingeschlossen.) Dies ist eine Funktion, die erwartet, dass der Stapel wie folgt aussieht:

a b c d

Beispielsweise:

1 '<' 10 2
@d@c@b[show d+][:c b tofunc!]while

Erläuterung

@d@c@b[show d+][:c b tofunc!]while
@d@c@b                               assign variables
               [............]while   while:
                :c                   duplicate "i" and push c
                   b tofunc!         convert b to a function and execute it
      [.......]                      do:
       show                          output "i" without popping
            d+                       and add the step to it
Conor O'Brien
quelle
4

C ++, 80

Hoppla, das ist C++nicht so C. War ein bisschen verwirrt von der Frage.

void f(int a,char b,int c,int d){for(;b==62?a>c:a<c;a+=d)cout<<a<<endl;}
Roman Gräf
quelle
Ist das C oder C ++?
Betseg
10
Welche Implementierung von C ++? (Ich bin gespannt, wie du etwas Ähnliches using namespace stdkostenlos bekommst ).
H Walters
Muss nicht ibei anfangen a, nicht 0? Sie können einfach aalles izusammen verwenden und überspringen und den ASCII-Wert von '>' verwenden. for(;b==62?a>c:a<c;a+=d)
Riley
Funktioniert nicht fürf(1,'<'3,1);
Roman Gräf
Ack ... ja, erfordert die Mathematik auf beiden Seiten; for(b-=61;b*a>b*c;a+=d)arbeitet für ein einzelnes Byte; aber das tut es auch for(;b-62?a<c:a>c;a+=d).
H Walters
4

C 52 51 Bytes

-1 Byte dank H Walters

f(a,b,c,d){for(;b&2?a>c:a<c;a+=d)printf("%d\n",a);}

Probieren Sie es online!

simon
quelle
1
Entschuldigen Sie den Fehler im Pseudocode, den ich nach jedem Druck inkrementiere :)
Sygmei
1
Verwenden Sie b&2statt b^60für ein anderes Byte.
H Walters
4

Python 3, 52 Bytes

def f(a,b,c,d):
 while[a>c,a<c][b<'>']:print(a);a+=d

repl.it

Jonathan Allan
quelle
Listen sinnvoll einsetzen!
Sygmei
4

Pip , 14 Bytes

W Va.b.ca:d+Pa

Übernimmt vier Befehlszeilenargumente. Unterstützt negative und Gleitkommazahlen sowie Vergleichsoperatoren < > = <= >= !=. Probieren Sie es online!

                a,b,c,d are cmdline args
W               While loop with the following condition:
  Va.b.c          Concatenate a,b,c and eval
            Pa  Print a with newline (expression also returns value of a)
        a:d+    Add d to that and assign back to a
DLosc
quelle
4

Gelee , 8 Bytes

ḢṄ+⁹;µV¿

Dies ist eine dyadische Verknüpfung, die a, b, c als linkes und d als rechtes Argument verwendet . Die Ausgabe kann unendlich sein und geht zu STDOUT.

Probieren Sie es online!

Wie es funktioniert

ḢṄ+⁹;µV¿  Dyadic link.
          Left argument:  a,b,c (integer, character, integer)
          Right argument: d     (integer)

       ¿  While...
      V     the eval atom applied to a,b,c returns 1:
     µ       Combine the links to the left into a chain and apply it to a,b,c.
Ḣ              Head; pop and yield a from a,b,c.
 Ṅ             Print a, followed by a linefeed.
  +⁹           Add a and the right argument (d) of the dyadic link.
    ;          Concatenate the result and the popped argument of the chain,
               yielding a+d,b,c.
Dennis
quelle
Befehlszeilenargumente verwenden die Python-Syntax und können nicht zwischen einem Zeichen und einer Singleton-Zeichenfolge unterscheiden. Wenn Sie CLAs verwenden möchten, müssen Sie ein einfügen F, um das Array zu reduzieren .
Dennis
2
Jetzt möchte ich die Hälfte meines Kommentars löschen, da er veraltet ist, während ich die andere Hälfte behalte. Ich denke, ich wiederhole einfach die relevante Hälfte und lösche den Rest: "Oh, bleh, du hast sie als Funktion definiert, damit du die implizite Ausgabe nach PPCG-Regeln ignorieren kannst. Daran hätte ich denken sollen."
4

Python 2 , 45 Bytes

exec"i=%d\nwhile i%c%d:print i;i+=%d"%input()

Probieren Sie es online!

Eine sehr wörtliche Umsetzung der Spezifikation. Übernimmt die Codevorlage, ersetzt die Eingaben durch Zeichenfolgenformatierung und führt sie aus.

xnor
quelle
4

Normaler TeX, 88 Bytes

\newcount\i\def\for#1 #2 #3 #4 {\i#1\loop\the\i\endgraf\advance\i#4\ifnum\i#2#3\repeat} 

Der Befehl \forstellt die angeforderte Funktion bereit. Speichern Sie dies als for.texund führen Sie es dann aus und geben Sie die Variablenwerte in der Befehlszeile ein: pdftex '\input for \for 1 < 5 1 \bye'Die Variablenwerte müssen durch Leerzeichen getrennt werden.

Musarithmie
quelle
4

Python 3, 61 Bytes

Einzeiler:

e=input;exec(f'i={e()}\nwhile i{e()}{e()}:print(i);i+={e()}')
G-Ox7cd
quelle
Willkommen auf der Seite! Gute Verwendung der neuen Literal-String-Interpolation. Ich denke, Sie können möglicherweise ein Byte speichern, indem Sie es \tdurch ein Leerzeichen ersetzen .
0 '28.
Vielen Dank. Noch die gleiche Größe nach dem Entfernen des \ n \ t nach dem dritten e ()
G-Ox7cd
3

Bash (+ Unix Tools), 29 Bytes

Golf gespielt

bc<<<"for(x=$1;x$2$3;x+=$4)x"

Prüfung

./forloop 1 '<' 10 1
1
2
3
4
5
6
7
8
9
Zeppelin
quelle
1
Ha. Ich wollte gerade genau das Gleiche posten ! +1
Digitales Trauma
3

Gemeines Lisp, 82 80 79 73 64 Bytes

(defmacro f(a b c d)`(do((i,a(+ i,d)))((not(,b i,c)))(print i)))

Prüfung

(f 1 < 10 1)

1 
2 
3 
4 
5 
6 
7 
8 
9 
NIL
CL-USER> 

-9 Bytes dank PrzemysławP.

Core-Dump
quelle
Vielleicht können Sie 9 Bytes einsparen, indem Sie ein Makro definieren. (defmacro f(a b c d)<insert backqoute here>(do((i,a(+ i,d)))((not(,b i,c)))(print i)))Verbrauch:(f 1 < 10 1)
@ PrzemysławP Nochmals vielen Dank!
Coredump
3

PHP, 69 65 Bytes

for(list(,$i,$b,$c,$d)=$argv);$b<"="?$i<$c:$i>$c;$i+=$d)echo"$i
";

Führen Sie mit '-r' aus; Geben Sie Befehlszeilenargumente als Eingabe ein.

Für nur ein Byte mehr 4 weitere Bytes kann ich jeden Operator nehmen:

for(list(,$i,$b,$c,$d)=$argv;eval("return $i$b$c;");$i+=$d)echo"$i
";

Ja, böse Eval. Wussten Sie, dass es etwas zurückgeben kann?


Durch die Destrukturierung in Kurzform [,$i,$b,$c,$d]=$argv;würden 4 weitere Bytes eingespart.
aber PHP 7.1 datiert die Herausforderung nach.

Titus
quelle
Ordentlich ! Ich war mir bei der Erstellung der Herausforderung nicht sicher, ob ich alle gemeinsamen Operatoren
einbeziehen
Woah, Eval ist böse.
Cyberbit
Es scheint mir, dass Sie PHP 7.1 verwenden können, um es zu verkürzen. Wenn es nicht so ist, listspart die Verwendung von 4 Bytes plus 4 Bytes mit kurzer Syntax
Jörg Hülsermann
@PHP 7.1 datiert die Challenge nach; aber danke für list().
Titus
2

Perl 6 , 44 Bytes

{.say for $^a,*+$^d...^*cmp$^c!= $^b.ord-61}

Wie es funktioniert

{                                          }  # A lambda.
          $^a                                 # Argument a.
             ,*+$^d                           # Iteratively add d,
                   ...^                       # until (but not including the endpoint)
                       *cmp$^c                # the current value compared to c
                                              # (less=-1, same=0, more=1)
                              != $^b.ord-61.  # isn't the codepoint of the b minus 61.
 .say for                                     # Print each number followed by a newline.

Wenn es in Ordnung ist, eine (möglicherweise unendliche) Folge von Zahlen als Wert vom Typ zurückzugeben Seq, anstatt die Zahlen auf stdout zu drucken, kann der .say forTeil entfernt und auf 35 Byte reduziert werden.

smls
quelle
2

Clojure, 66 63 Bytes

#(when((if(= %2"<")< >)% %3)(println %)(recur(+ % %4)%2 %3 %4))

-3 Bytes durch Ausklammern der loop. Ich "missbrauche" den init-Parameter, um als laufender Akku zu fungieren.

Rekursive Lösung (mit TCO). Siehe Kommentare in vorprogrammiertem Code. Ich habe eine nicht-TCO-rekursive Lösung ausprobiert, die 67 Byte umfasste.

Ich würde diesen Beat gerne in Clojure sehen! Ich denke das ist das kleinste was ich bekommen kann.

(defn my-for [init-num com-str com-num inc-num]
  (let [op (if (= com-str "<") < >)] ; Figure out which operator to use
    (when (op init-num com-num) ; When the condition is true, print and recur
      (println init-num)
      (recur (+ init-num inc-num) com-str com-num inc-num))))
    ; Else, terminate (implicit) 
Karzigenat
quelle
Oh, ich habe diese Antwort nicht bemerkt. #(when(({">">"<"<}%2)% %3)(println %)(recur(+ % %4)%2 %3 %4))würde 61 Bytes sein und dein whenmit meinem kombinieren ({">">"<"<}%2).
NikoNyrh
2

Groovy, 51 Bytes

{a,b,c,d->while(Eval.me("$a$b$c")){println a;a+=d}}

Dies ist eine namenlose Schließung. Probieren Sie es online!

Achtung - Wenn Sie dies mit testen möchten groovy console, stellen Sie sicher, dass Sie den gesamten Prozess abbrechen, wenn die Eingabe eine Endlosschleife verursacht. Ich bemerkte dies, nachdem es ~ 5 GB RAM verbraucht hatte.

Gurupad Mamadapur
quelle
2

QBIC , 51 bis 40 Bytes

:;::{?a┘a=a+c~A=@<`|~a>=b|_X]\~a<=b|_X

Und drei Minuten nach dem Posten wurde mir klar, dass ich die Terminatorlogik vereinfachen könnte ...

:;::      Consecutively read a, A$, b and c from the command line
{?a┘      Start an infinite loop; print a, add a newline to the source
a=a+c     increment a
~A=@<`|   If we are in LESS THAN mode
  ~a>=b   and IF we are no longer LESS
    |_X]  THEN QUIT, end if.
  \       ELSE (we're in GREATER THAN mode)
    ~a<=b IF we are no longer GREATER
    |_X   THEN QUIT
          The last IF and the loop are auto-closed
steenbergh
quelle
2

Batch, 94 Bytes

@set i=%1
@set o=gtr
@if "%~2"=="<" set o=lss
:g
@if %i% %o% %3 echo %i%&set/ai+=%4&goto g

Wenn das Verhalten des zweiten Parameters nicht gegeben wäre, könnte dies in 53 Bytes erfolgen:

@for /l %%i in (%1,%4,%n%)do @if not %%i==%3 echo %%i

Das macht einfach nichts, wenn der Schritt das falsche Vorzeichen hat. Der zusätzliche Test besteht darin, dass die forSchleife von Batch ermöglicht, dass die Schleifenvariable dem Endwert entspricht.

Neil
quelle
2

Clojure, 66 Bytes

#(loop[i %](if(({">">"<"<}%2)i %3)(do(println i)(recur(+ i %4)))))

Dies könnten 55 Bytes gewesen sein <und >sind Funktionen in Clojure:

(def f #(loop[i %](if(%2 i %3)(do(println i)(recur(+ i %4))))))
(f 1 < 10 1)
NikoNyrh
quelle
Ich mag die Verwendung der Karte hier. Ich hätte nie gedacht, dass das meinen Weg geschlagen hätte. Interessant ist auch, dass unsere beiden Anfangszählungen trotz leicht unterschiedlicher Herangehensweisen gleich waren.
Carcigenicate
Das Zulassen von b als Funktion würde einigen Sprachen einen unfairen Vorteil verschaffen :)
Sygmei
Stimmt, aber ich denke, die meisten Sprachen, die ich kenne, würden nicht viel davon profitieren, <anstatt "<"Clojure zuzulassen .
NikoNyrh
@ Sygmei True. Es wäre allerdings verdammt süß. Ich kann Ihnen nicht die Schuld geben, dass Sie diesen Anruf getätigt haben.
Carcigenicate
OP besagte Zeichen sind in Ordnung anstelle von Zeichenketten für die Vergleichsoperatoren übrigens. Das sollte ein paar Bytes sparen.
Carcigenicate
2

TI-Basic, 41 34 Bytes

Prompt A,Str2,Str3,D
While expr("A"+Str2+Str3
Disp A
A+D->A
End
Timtech
quelle
1
So wie ein TI-Rechner funktioniert, werden viele Symbole als einzelnes Byte gespeichert. Prompt , Str2, Str3, While , expr(, Disp , ->, Und Endsind alle Single-Byte - Zeichen. Ich zähle 29 Bytes.
Pavel
@Pavel Vielen Dank für Ihr Interesse! Obwohl es stimmt, dass TI-Basic tokenisiert ist, bestehen nicht alle Token aus einem Byte. Zum Beispiel Str2, Str3und expr(sind alle Zwei-Byte - Token. Eine Liste der Ein-Byte-Token finden Sie unter tibasicdev.wikidot.com/one-byte-tokens
Timtech