Analysieren Sie eine Liste mit vorzeichenbehafteten unären Zahlen

16

Unäre Zahlen stellen normalerweise nur nichtnegative Ganzzahlen dar. Sie können jedoch wie folgt erweitert werden, um alle Ganzzahlen darzustellen:

  • Eine positive ganze Zahl N wird als N dargestellt 1:5 -> 11111
  • Eine negative ganze Zahl -N wird als 0gefolgt von N dargestellt 1:-5 -> 011111
  • Null wird dargestellt als 0

Wir können dann eine Liste dieser Zahlen eindeutig darstellen, wenn wir 0als Trennzeichen verwenden:

3,-2,0,1
111,011,0,1
111 0 011 0 0 0 1
11100110001

Ihre Aufgabe: Nehmen Sie eine Zeichenfolge, die eine solche Liste mit vorzeichenbehafteten unären Zahlen darstellt, und übersetzen Sie sie in eine Liste mit Dezimalzahlen.

Einzelheiten

Sie können davon ausgehen, dass die Eingabe eine vollständige Liste von vorzeichenbehafteten unären Zahlen ist. Insbesondere muss Ihr Programm nicht 1) leere Eingaben oder 2) Eingaben verarbeiten, die mit einem Trennzeichen enden.

Sie können davon ausgehen, dass die Größe jeder Zahl 127 nicht überschreitet. Bei Sprachen mit maximaler Größe von Zeichenfolgen oder Listen können Sie davon ausgehen, dass die Eingabe und Ausgabe in die Datenstrukturen Ihrer Sprache passen, aber Ihr Algorithmus sollte theoretisch für eine Liste von funktionieren alle Größen.

Ihr Programm oder Ihre Funktion kann E / A auf eine der Standardweisen ausführen . Die Eingabe kann eine Zeichenfolge oder eine Liste von Zeichen, Einzelzeichenfolgen, Ganzzahlen oder Booleschen Werten sein. Sie können zwei beliebige Zeichen verwenden, um 1und zu repräsentieren 0. wenn Sie nicht verwenden , 1und 0geben Sie bitte an, welche Zeichen Sie verwenden.

Die Ausgabe muss aus Dezimalzahlen in einem angemessenen Listenformat bestehen (insbesondere muss eine Art Trennzeichen zwischen den Zahlen bestehen). Negative Zahlen sollten mit einem Minuszeichen angezeigt werden. Wenn Ihre Sprache jedoch ein anderes Format für negative ganze Zahlen hat, akzeptiere ich das auch. Null kann in der Ausgabe als 0oder dargestellt werden -0.

Testfälle

1 -> 1
0 -> 0 (or -0, and similarly for the other test cases)
011 -> -2
1101 -> 2,1
1100 -> 2,0
11001 -> 2,-1
110001 -> 2,0,1
11100110001 -> 3,-2,0,1
00000001 -> 0,0,0,-1
01111011111111001111111111111110111111111111111100111111111111111111111110111111111111111111111111111111111111111111 -> -4,8,-15,16,-23,42
01111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111 -> -127
DLosc
quelle
2
Nitpick: Da dies enthält '0's, ist es technisch nicht einheitlich. Gute Herausforderung!
DJMcMayhem
4
@DJMcMayhem Nitpick zum Nitpick: Ich habe technisch nie gesagt, dass es unärgerlich ist. Es ist eine Erweiterung von unary, die ich "Unary" nenne. ;)
DLosc
@DJMcMayhem IMO, die Herausforderung besteht speziell darin, dass das Trennzeichen ( 0) und das negative Vorzeichen ( 0) dasselbe sind, obwohl es immer noch eindeutig ist, da Sie keine negativen Vorzeichen in der Mitte einer Zahl haben können (ist 182--693-1eine Zahl? Nein, und auch nicht 1111011000101111aus genau demselben Grund).
Erik der Outgolfer
Ist es in Ordnung, wenn die ausgegebene Liste in umgekehrter Reihenfolge zur Eingabe ist?
DJMcMayhem
Nun,

Antworten:

10

Python 2 , 73-70 Bytes

Eine Funktion, die eine Zeichenfolge als Eingabe verwendet und eine Zeichenfolgendarstellung einer Python-Liste zurückgibt. Null kann sowohl durch 0als auch -0(wenn es zuletzt kommt) dargestellt werden:

lambda s:`map(len,s.split('0'))`.replace('0, ','-').replace('--','0,')

Erläuterung

  1. splitdie Eingabezeichenfolge sauf Nullen.
  2. Nimm die Länge jeder Zeichenkette in der resultierenden Liste (mit map).

Das ist ein langer Weg. Schließlich waren Nullen Trennzeichen. Und die Zahlen waren unärgerlich, also lenwandeln Sie diese bequem in Dezimalzahlen um. Aber jetzt haben wir alle Nicht-Trennzeichen-Verwendungen von durcheinander gebracht 0. Glücklicherweise waren alle Verwendungen ohne Trennzeichen führende Nullen, sodass sie nach einer Trennzeichen-Null kamen und uns Zeichenfolgen mit der Länge Null gaben ( '00'.split('0') == ['', '', '']). Diese Zero-Length-Strings wurden dann auch 0wegen der len.

  1. Verwandle die Liste in einen String ( mit "umgekehrten Anführungszeichen" ), damit wir das Durcheinander leichter beheben können.
  2. replaceJede Null, die einer anderen Zahl vorausgeht, erhält stattdessen ein negatives Vorzeichen. Das behebt die Verwendung von 0als Zeichen, bricht aber die wörtlichen Nullen. Literalen Nullen wurde ebenfalls ein Trennzeichen vorangestellt, sodass sie jetzt bei der nächsten Zahl zu Strichpaaren werden.
  3. replacejeweils --wieder in ein 0Element in der "Liste".
Mercator
quelle
1
Willkommen bei PPCG!
Steadybox
Dies ist ein wirklich kreativer Ansatz! Vielleicht möchten Sie eine kurze Erklärung hinzufügen, damit auch diejenigen, die kein Python sprechen, Ihre Antwort schätzen können.
DLosc
@ DLosc, danke, ich wusste nichts über das Backtick. Wortreiche Erklärung auch hinzugefügt.
mercator
8

Netzhaut , 23 21 Bytes

(.)0
$1 
01
-1
1+
$.&

Probieren Sie es online!

Die erste Stufe (.)0<newline>$1<space>entspricht einem beliebigen Zeichen, gefolgt von einem 0. Die Übereinstimmung wird durch das erste Zeichen gefolgt von einem Leerzeichen ersetzt. Dadurch wird die Zeichenfolge in die einzelnen Zahlen aufgeteilt.

Die zweite Stufe 01<newline>-1ersetzt 0's vor einem Block von 1' s bis zum -Zeichen.

In der letzten Phase werden 1+<newline>$.&alle Blöcke von 1's abgeglichen und durch die Länge der Gruppe ersetzt.

Hier ein Beispiel mit der Ausgabe der einzelnen Stufen.

ovs
quelle
Sehr schön - alle meine Ideen scheinen bei 24 Bytes
Neil
1
Könnten Sie bitte eine Erklärung hinzufügen? Ich spreche keine Retina.
Daniel
@Dopapp hat eine Erklärung hinzugefügt
ovs
7

Vim, 56 Bytes

:s/\v(0?1*)0?/\1\r/g|%s/0/-/|%s/1*$/\=len(submatch(0))
D

Probieren Sie es online!

Ich habe eine Weile nicht mehr in vim gepostet. Ich benutze meistens Vim, weil V manchmal ein Schmerz ist. Da der countBefehl, mit dem die Anzahl der Einsen in der Zeile ermittelt werden kann, alle Nullen in der Zeile überschreibt, können wir ihn anschließend nicht mehr negieren.

Erläuterung:

Dies ist ein Byte kürzer als auf einfache Weise:

:s/\v(0?1*)0?/\1\r/g
:%s/0/-
:%s/1*$/\=len(submatch(0))
D

aufgrund der Befehlsverkettung. Da dieser die Befehle trennt, verwende ich ihn zur Erklärung.

:s/                     " Substitute
                        " Search for...
   \v                   "   Enable 'magic'. This determines whether certain atoms require a backslash or not.
                        "   Without it we would have: '\(0\?1*\)0\?', which is 2 bytes longer
      0?                "   An optional 0
        1*              "   Followed by any number of '1's
     (    )             "   (call that group 1)
           0?           "   Followed by another optional 0
             /          " Replace it with...
              \1        "   Subgroup 1
                \r      "   A newline
                  /g    " Do this for every match on the current line.

Jetzt steht jede vorzeichenbehaftete unäre Nummer in einer eigenen Zeile. Am Beispiel von '11100110001' haben wir an dieser Stelle:

111
011
0
1

:%s/0   " Replace every 0
     /- " With a dash  

:%s/1*$/                    " Replace every run of 1's at the end of a line
        \=len(submatch(0))  " With the length of said run

Da wir am Ende jedes Matches neue Zeilen hinzugefügt haben, hatten wir eine leere Zeile, bevor wir diese ausgeführt haben. Nachdem Sie dies ausgeführt haben, erhalten Sie eine '0' (da diese einer Anzahl von 0 '1 entspricht). Also rufen wir einfach Dan, um diese Zeile zu löschen und lassen sie leer

DJMcMayhem
quelle
Pfui. :%s/1+$/+
Würden
@NieDzejkob Ich verstehe nicht, warum das kürzer wäre. Und auch, das würde -anstelle von 0oder geben-0
DJMcMayhem
Ich wollte die letzte Zeile auf diese Weise entfernen: P, egal.
NieDzejkob
7

Haskell , 68 66 Bytes

f(x:r)|(a,b)<-span(>0)r=([(0-),(1+)]!!x$sum a):[z|_:t<-[b],z<-f t]

Probieren Sie es online! Nimmt die Eingabe als Liste von Nullen und Einsen. Anwendungsbeispiel: f [0,0,0,1,1]Erträge [0,-2].

Erläuterung:

Die Musterübereinstimmung in wird f(x:r)|(a,b)<-span(>0)ran xdas erste Element der Eingabe, aan eine (möglicherweise leere) Liste der folgenden 1s und ban den Rest der Eingabe gebunden. Bei einem gegebenen Eingang [0,1,1,1,0,0,1], bekommen wir x=0, a=[1,1,1]und b=[0,0,1].

Die aktuelle Zahl ist dann entweder die Summe aus anegiertem if x=0oder die Summe aus aplus eins if x=1. Dies wird erreicht, indem mit xin eine Liste indexiert wird, die eine Negations- und Inkrementierungsfunktion enthält, und die resultierende Funktion auf die Summe von a: angewendet wird [(0-),(1+)]!!x$sum a.

Die Restliste bist entweder leer oder enthält eine trennende Null und die nächste Zahl. Das Listenverständnis [z|_:t<-[b],z<-f t]versucht, bauf das Muster abzustimmen _:t, dh das head-Element zu vergessen und den Rest der Liste daran zu binden t. Wenn bleer, schlägt diese Übereinstimmung fehl und das Listenverständnis wird zu ausgewertet. Dies []ist der Basisfall für die Rekursion. Ansonsten wird die Funktion frekursiv angewendet tund das Listenverständnis wertet zaus dem Ergebnis von auf alle Elemente aus f t.

Laikoni
quelle
3

Wolfram Language (Mathematica) , 80 Byte

StringCases[#<>"0",x_~~Shortest@y___~~"0":>(If[x=="0",-#,#+1]&)@StringLength@y]&

Probieren Sie es online!

Missbraucht die Mechanik von StringCases, da sie überlappende Muster nicht prüft. Da wir ohne Überlappungen von links nach rechts suchen, erhalten wir immer nur die Ganzzahlen, die wir benötigen.

Erläuterung

#<>"0"

Fügen Sie am Ende eine Null hinzu

StringCases

Finde alle folgenden Muster ...

x_~~Shortest@y___~~"0"

Ein einzelnes Zeichen (call it x), gefolgt von der kürzestmöglichen Zeichenfolge mit der Länge Null oder einer längeren Zeichenfolge (call it y), gefolgt von einer Null.

(If[x=="0",-#,#+1]&)@StringLength@y

Auf passendes Muster auftragen: Länge von y. Wenn xNull ist, negieren Sie den Wert. Sonst inkrementiere eins.

Dies gilt 00auch, da ydies eine leere Zeichenfolge wäre und wir berechnen würden -0( == 0).

JungHwan min
quelle
3

Brain-Flak , 94 (70?) Bytes

([]){{}({(<()>)()}{}(<>)<>{<([{}]<>{})><>})
{{}<>([{}])(<>)}{}{}([])}{}<>([]){{}({}<>)<>([])}<>

Probieren Sie es online!

Dies ist eigentlich überraschend knapp für Brain Flak.

Hier ist eine kommentierte / lesbare Version:

([])

{

    #Pop the Stack height
    {}

    (
        #If there isn't a leading 0, evaluate to 1...
        {
            (<()>)

            ()
        }

        #Pop the 0
        {}

        #Push a 0 onto the alternate stack
        (<>)
        <>

        #Run of '1's
        {
            #Decrement the alternate stack
            <([{}]<>{})>
            <>
        }

        #And push it here
    )

    #Was there a not leading 0?

    {
        {}

        #Invert the value on the alternate stack
        <>([{}])(<>)
    }

    #Pop 2 zeros
    {}{}


    ([])

}{}<>

#Push stack height
([])

#Reverse the stack
{

    {}

    ({}<>)

    <>([])

}<>

Wenn die Ausgabe umgekehrt sein kann, können wir dies stattdessen für 70 tun:

([]){{}({(<()>)()}{}(<>)<>{<([{}]<>{})><>}){{}<>([{}])(<>)}{}{}([])}<>

Dieser Tipp von mir ist fast perfekt für diese Situation. Aber es funktioniert nicht ganz, da wir eine 0 drücken müssen, bevor wir die Operation ausführen (die Einsen zählen) und die Operation in einer Schleife abläuft. Der kürzeste Weg, diesen Tipp zu verwenden, ist:

([]){{}({(<()>)()}{}(<>)<>{<([{}]<>{})><>})
{{}<>([{}])(<>)}{}{}(<>())<>([])}{}<>{{}({}<>)<>}<>

Das sind auch 94 Bytes.

DJMcMayhem
quelle
3

Schale , 20 18 17 15 14 Bytes

Γ~:?Σṁ_Πȯ₀tΣġ/

Probieren Sie es online!

Erläuterung

Γ~:?Σṁ_Πȯ₀tΣġ/  Input is a list, say x = [0,1,1,0,0,0,1,1]
            ġ   Group by
             /  division.
                This splits x right before each 0: [[0,1,1],[0],[0],[0,1,1]]
Γ               Deconstruct into head y = [0,1,1] and tail z = [[0],[0],[0,1,1]]
   ?Σṁ_Π        Apply to y:
       Π         Product: 0
   ?Σ            If that is nonzero, take sum of y,
     ṁ_          else take sum of negated elements of y: u = -2
        ȯ₀tΣ    Apply to z:
           Σ     Concatenate: [0,0,0,1,1]
          t      Drop first element: [0,0,1,1]
         ₀       Recurse: [0,2]
 ~:             Tack u to the front: [-2,0,2]

Die Aufteilung funktioniert so. ġ/teilt sein Argument auf jedes Elementpaar auf, a,bfür das /a bes falsch ist. /a bist eine Division mit gespiegelten Argumenten, also bgeteilt durch a. Die relevanten Werte in diesem Programm sind:

  • /1 1gibt 1(wahr).
  • /1 0gibt 0(falsch).
  • /0 1gibt Inf(positive Unendlichkeit, wahr).
  • /0 0gibt Any(ein spezieller NaN-ähnlicher Wert, falsch).
Zgarb
quelle
3

Acc !! , 252 237 Bytes

N
Count i while _/48 {
Count n while 48/_ {
Write 45
50+N
}
_+49/_*50
Count u while _%50/49 {
_+100-_%50+N
}
_/50-1
Count h while _/200 {
Write _/200+48
_%200+1
}
Count t while _/20+_%2 {
Write _/20+48
_%20-_%2
}
Write _/2+48
Write 9
N
}

Verwendet -0. Gibt durch Tabulatorzeichen getrennte Zahlen mit einem nachgestellten Tabulator aus. Probieren Sie es online!

Zeitaufwand für das Schreiben des eigentlichen Algorithmus: 20 Minuten. Zeitdauer für das Debuggen meines dezimalen Ausgabecodes: 45 Minuten. : ^ P

Mit Kommentaren

Ich weiß nicht, ob diese Kommentare den Code sehr gut erklären - sie basieren auf meinen Notizen, die ich mir während des Schreibens gemacht habe, und setzen daher ein gewisses Verständnis dafür voraus, wie Acc !! funktioniert. Wenn etwas näher erläutert werden muss, lassen Sie es mich wissen und ich werde versuchen, es klarer zu machen.

# We partition the accumulator _ as [number][flag][nextchar]
# [flag] is a 2-value slot and [nextchar] a 50-value slot
# So [nextchar] is _%50, [flag] is _/50%2, [number] is _/100
# [flag] is 1 if we're in the middle of reading a number, 0 if we're between numbers
# It is also used for outputting as decimal (see below)
# Possible input characters are 0, 1, and newline, so [nextchar] is 48, 49, or 10

# Read the first character
N
# Loop while the character we just read is 0 or 1 and not newline
Count i while _/48 {
  # What we do in the loop depends on the combination of [flag] and [nextchar]:
  # 0,48 (start of number, read 0) => write minus sign, [flag] = 1, read another char
  # _,49 (read 1) => increment [number], [flag] = 1, read another char
  # 1,48 (middle of number, read 0) => write/clear [number], status = 0, read another
  #      char
  # 1,10 (middle of number, read <cr>) => ditto; the next read will be 0 for eof, which
  #      means the acc will be less than 48 and exit the loop

  # Process leading 0, if any
  Count n while 48/_ {
    # acc is 48: i.e. [number] is 0, [flag] is 0, [nextchar] is 48 (representing a 0)
    # Output minus sign
    Write 45
    # Set [flag] to 1 (thereby exiting loop) and read [nextchar]
    50+N
  }
  # If number starts with 1, then we didn't do the previous loop and [flag] is not set
  # In this case, acc is 49, so we add (50 if acc <= 49) to set [flag]
  _+49/_*50

  # Process a run of 1's
  Count u while _%50/49 {
    # [nextchar] is 49 (representing a 1)
    # Increment [number] and read another
    _+100-_%50+N
  }

  # At this stage, we know that we're at the end of a number, so write it as decimal
  # This is "easier" (ha) because the number has at most three digits
  # We shift our partitioning to [number][flag] and set [flag] to 0
  _/50-1

  # Output hundreds digit if nonzero
  # Since [number] is _/2, the hundreds digit is _/200
  Count h while _/200 {
    Write _/200+48
    # Mod 200 leaves only tens and units; also, set [flag] to 1
    _%200+1
  }
  # Output tens digit (_/20) if nonzero OR if there was a hundreds digit
  # In the latter case, [flag] is 1
  Count t while _/20+_%2 {
    Write _/20+48
    # Mod 20 leaves only units; clear [flag] if it was set
    _%20-_%2
  }
  # Write units unconditionally
  Write _/2+48

  # Write a tab for the separator
  Write 9
  # Read another character
  N
}
DLosc
quelle
2

Python 2 , 96 92 Bytes

lambda s:[[len(t),-len(t)+1]['1'>t]for t in s.replace('10','1 ').replace('00','0 ').split()]

Probieren Sie es online!

Danke an ovs und DLosc für jeweils 2 Bytes.

Chas Brown
quelle
2

R , 119 Bytes

function(x){n=nchar
y=regmatches(x,regexec("(0?)(1*)0?([01]*)",x))[[1]]
cat((-1)^n(y[2])*n(y[3]),"")
if(y[4]>0)f(y[4])}

Probieren Sie es online!

Der Code verwendet diese Lösung von stackoverflow für ein verwandtes Problem (Danke an eifersüchtige für die Idee). Die Ausgabe ist eine durch Leerzeichen getrennte Zeichenfolge, die auf stdout gedruckt wird.

NofP
quelle
2

Jelly ,  19  18 Bytes

Es muss einen besseren Weg geben ...

®ḢN$Ḣ©?ṄEȧ
ṣ0L€ÇL¿

Ein vollständiges Programm druckt jede Nummer, gefolgt von einem Zeilenvorschub.

Probieren Sie es online!

Wie?

®ḢN$Ḣ©?ṄEȧ - Link 1, print first number and yield next input: list of numbers, X
           -                              e.g. [8,0,15,16,...] or [0,4,8,0,15,16,...]
      ?    - if...
    Ḣ      - condition: yield head and modify  8([0,15,16,...])   0([4,8,0,15,16,...])  
     ©     -            (copy to register)     8                  0
®          - then: recall from the register    8
   $       - else: last two links as a monad:
 Ḣ         -         yield head and modify                        4([8,0,15,16,...])
  N                  negate                                      -4
       Ṅ   - print that and yield it           8                 -4
        E  - all equal (to get 0 to be truthy) 1                  1
         ȧ - AND the (modified) input          [0,15,16,...]      [8,0,15,16,...]
           -   (ready to be the input for the next call to this link)

ṣ0L€ÇL¿ - Main link: list e.g. [0,1,0,0,0,0,1,1]
ṣ0      - split at zeros       [[],[1],[],[],[],[1,1]
  L€    - length of €ach       [0,1,0,0,0,2]
      ¿ - while...
     L  - condition: length                           1  1  1  0  ([0,1,0,0,0,2], [0,0,0,2], [0,2], [])
    Ç   - action: call the last link (1) as a monad  -1  0 -2     ( - 1            - 0        - 2)
Jonathan Allan
quelle
1

QBasic, 88 86 Bytes

1u$=INPUT$(1)
z=u$<"1
IF n*z THEN?(1-2*s)*(n-s):s=0:n=0ELSE s=s-z:n=n+1
IF"!"<u$GOTO 1

Das hat Spaß gemacht. Mehrere Revisionen ab einer 107-Byte-Version führten zu einem der am meisten verschleierten Teile von QBasic, die ich je geschrieben habe. (Edit: Seltsamerweise konnte ich 2 Bytes Golf spielen, indem ich den Code klarer machte.)

Hinweis: Dieses Programm liest die Benutzereingaben einzeln, ohne sie auf dem Bildschirm wiederzugeben (Ergebnis der Verwendung INPUT$(1)anstelle der üblichen INPUTAnweisung). Während Sie tippen, werden die Einsen und Nullen nicht angezeigt, aber die Dezimalzahlen werden angezeigt, während sie berechnet werden. Stellen Sie sicher, dass Sie Enteram Ende der Eingabe drücken, um die letzte Zahl zu sehen und das Programm zu beenden.

Ungolfed-Version

sign = 0
num = 0
DO
  digit$ = INPUT$(1)
  isZero = (digit$ < "1")
  IF num > 0 AND isZero THEN
    PRINT (1 - 2 * sign) * (num - sign)
    sign = 0
    num = 0
  ELSE
    IF isZero THEN sign = 1
    num = num + 1
  END IF
LOOP WHILE "!" < digit$

Erläuterung

(AKA "Was? Das macht doch keinen Sinn!")

Die Grundstrategie besteht darin, eine Schleife auszuführen, die INPUT$(1)jedes Mal ein Zeichen !abruft, Dinge damit erledigt und so lange eine Schleife durchläuft, wie das Zeichen einen größeren ASCII-Wert hat als der von (dh, es war kein Zeilenumbruch).

Wir verfolgen die laufenden Zahlen mit zwei Variablen. numist die Anzahl der Zeichen in der aktuellen vorzeichenbehafteten unären Zahl (einschließlich einer führenden Null). signist, 1wenn die Zahl eine führende Null hatte, 0wenn nicht. Beide müssen auf initialisiert werden 0, was für die Golf-Version sehr gut ist, da numerische Variablen in QBasic automatisch auf initialisiert werden 0.

Wann immer wir ein Zeichen lesen, ist das erste, zu bestimmen, ob es 1oder ist 0. Wir verwenden dieses Ergebnis zweimal und speichern es in isZero. Technisch gesehen ist dieser Name irreführend, da der Wert auch dann wahr ist, wenn das Zeichen ein Zeilenumbruch ist. Beachten Sie, dass in QBasic -1wahr und falsch ist0 .

Wenn wir gerade eine Zahl ( num > 0) lesen und eine Null oder ein Ende der Eingabe ( isZero) erreichen, müssen wir berechnen, welche Zahl wir gelesen haben.

  • signspeichert 0für positiv, 1für negativ. Um 1zum Positiven und -1zum Negativen zu gelangen, brauchen wir1-2*sign .
  • numspeichert die richtige Größe für Positive, aber eine mehr als die Größe für Negative (da sie die Vorzeichenmarkierung enthält). So können wir num-signfür die Größe verwenden.

Multiplizieren Sie diese und drucken Sie; dann zurücksetzen signund numauf 0in Vorbereitung auf das Lesen der nächsten Nummer.

Andernfalls (wenn wir keine Null erreicht haben oder wenn wir am Anfang einer Zahl eine Null erreicht haben) aktualisieren wir signund numwie folgt:

  • signwird, 1wenn wir auf eine führende Null schauen; ansonsten bleibt es, wenn wir uns eine anschauen, bei dem, was es schon war. Der Golf-Code lautet s=s-z:
    • Wenn dies eine führende Null ist, zist -1. Da swird garantiert 0(da dies der Beginn einer neuen Nummer ist), s-zsein 1.
    • Wenn dies eine Eins ist, zist 0. Dann s-zbleibt um jeden Wert shatte zuvor.
  • num wird inkrementiert.

Das ist es!

DLosc
quelle
0

JavaScript (ES6), 60 Byte

Gibt eine durch Leerzeichen getrennte Liste von Ganzzahlen zurück.

s=>(0+s).replace(/00?1*/g,s=>(l=s.length,+s[1]?l-1:2-l)+' ')

Testfälle

Arnauld
quelle
0

Lua , 58 Bytes

(...):gsub("(0?)(1*)0?",function(s,n)print(#n-2*#s*#n)end)

Probieren Sie es online!

Vollständiges Programm, nimmt Eingaben von der Kommandozeile entgegen und druckt die Zahlen durch Zeilenumbrüche getrennt auf stdout.

Jonathan S.
quelle