Visualisieren Sie lange Teilung mit ASCII-Kunst

16

Schreiben Sie ein Programm, das die lange Teilung mit ASCII-Kunst visualisiert. Die Eingabe besteht aus zwei Ganzzahlen, einem Zähler und einem Nenner, wobei das Eingabeformat Ihrer Wahl verwendet wird.

Beispiele:

1234 ÷ 56:

     22
   ----
56|1234
   112
   ---
    114
    112
    ---
      2

1002012 ÷ 12:

     83501
   -------
12|1002012
    96
   ---
     42
     36
     --
      60
      60
      --
        12
        12
        --

0 ÷ 35

   0
   -
35|0

Regeln:

  • Die Verwendung des Divisionsoperators der Programmiersprache ist zulässig.
  • Die Verwendung von Big Integer-Unterstützung ist ebenfalls zulässig.
  • Für die Konsistenz:
    • Wenn der Quotient Null ist, drucken Sie eine einzelne Null am Ende des Sprungbretts.
    • Wenn der Rest Null ist, drucken Sie ihn nicht aus.
    • Drucken Sie keine führenden Nullen auf Zahlen.
  • Überzählige Zeilenumbrüche am Ende und Leerzeichen nach rechts sind zulässig.
  • Lösung mit den wenigsten Zeichen gewinnt.

Grenzen:

  • 0 <= Zähler <= 10 72 - 1
  • 1 <= Nenner <= 9999999

Dies bedeutet, dass die Ausgabe niemals breiter als 80 Spalten sein wird.

Testsuite und Beispielimplementierung:

Sie können long-division.c ( gist ) verwenden, um Ihr Programm zu testen. Es ist eigentlich ein Bash-Skript mit einem darin enthaltenen C-Programm. Optimieren Sie es, um Ihr Programm in der Testsuite aufzurufen. Sehen Sie sich den C-Code unten an, um die Referenzimplementierung zu sehen. Bitte lassen Sie mich wissen, wenn es Probleme mit dem Beispielprogramm oder der Testsuite gibt.

$ ./long-division.c 10 7
   1
  --
7|10
   7
  --
   3
$ ./long-division.c
PASS 1234 ÷ 56
PASS 1002012 ÷ 12
PASS 1 ÷ 1
--- snip ---

Score: 35 / 35
All tests passed!

Bearbeiten: Auf Wunsch stelle ich die Eingabe und erwartete Ausgabe der Testsuite in Textdateien ( gist ). Beispielnutzung (Bash):

cat input | while read nd; do
    ./program $nd |
        sed 's/\s*$//' | sed -e :a -e '/^\n*$/{$d;N;};/\n$/ba'
done > output

diff -u expected output

Die seltsamen sed-Befehle filtern nachgestellte Zeilenumbrüche und Leerzeichen aus der Programmausgabe heraus.

Joey Adams
quelle
Ich habe einen kleinen Fehler in der Referenzimplementierung entdeckt, nämlich im Fall von 123000123000123 ÷ 123. Die Subtraktionslinien überspannten Leerzeichen, sollten aber nur die Länge der sichtbaren Ziffern des Minuends überspannen. Es ist jetzt behoben.
Joey Adams
2
Ich denke, die Ausgabe ist etwas voreingenommen gegenüber dem englischsprachigen
Golfpublikum
Können Sie einfach eine Datei erstellen, die die erwartete Ausgabe aller Tests anzeigt und mit dieser verknüpft ist?
Mellamokb
@mellamokb: Hinzugefügt, danke!
Joey Adams
Was ist mit akzeptieren? Die Frage ist alt genug ...
Oleh Prypin

Antworten:

3

Python 3, 284 257 Zeichen

div.py

n,t=input().split()
d=int(t)
l=lambda x:len(str(x))
s=l(n)
def p(x):print(' '*(l(d)+s-l(x)+1)+str(x))
p(int(n)//d)
p('-'*s)
p(t+'|'+n)
s=z=f=0
while t:
 try:
  while z<d:z=z*10+int(n[s]);s+=1
 except:t=0
 if z*f:p(z)
 if t:f=1;t=z//d*d;p(t);p('-'*l(z));z-=t

Verwendung: python3 div.py
Eingabe: über Tastatur

test.py

import sys
sys.stdin=open('input'); sys.stdout=open('output','w')
for line in open('input'): exec(open('div.py').read())

Output- Übereinstimmungen werden erwartet

Versionen:
 1. 284
 2. 257 : s,z,f=0,0,0s=z=f=0; z and fz*f; besseres Looping; ein paar Zeilenumbrüche entfernt.

Oleh Prypin
quelle
2
Sie können Ideone für Python3 und Input versuchen - ideone.com/clone/ZZyzu
YOU
3

Haskell, 320 Zeichen

l=length
(®)=replicate
p!v=p&show v
p&s=(p-l s)®' '++s
0§_=[];_§l=l
d[m,n]=l c!(read m`div`e):l c&(l m®'-'):c:drop 1(g 0(map(toInteger.fromEnum)m)$1+l n)where
 e=read n;c=n++'|':m
 g r(d:z)p=i§[o!k,o!(i*e),o&(l(show k)®'-')]++g j z o where k=r*10+d-48;(i,j)=k`divMod`e;o=1+p
 g r[]p=r§[p!r]
main=interact$unlines.d.words

Besteht alle Tests. Während ist das schön Golf'd - ich denke, es gibt hier noch mehr zu tun ...


  • Bearbeiten: (344 -> 339) readAnrufe verzögern , wodurch der Anrufbedarf verringert wird showund sich die Abkürzung showals snicht lohnt.
  • Bearbeiten: (339 -> 320) Formatierungsfunktionen für Zeichenfolgenfelder wurden neu geschrieben
MtnViewMark
quelle
Ordentlich! Ich habe eine Haskell-Lösung mit 344 Zeichen erstellt, sie aber nicht veröffentlicht. Außerdem wusste ich nicht, dass Sie Unicode-Symbole für Operatoren (ohne -XUnicodeSyntax) verwenden können.
Joey Adams
3

JavaScript (400 394 418 )

function d(n,d){t=parseInt;p=function(v){return(s+v).substring(v.length)};a=function(v,c){return v.replace(/\d/g,c)};w='\n';q=b=o=c=e='';s=a(d,' ')+' ';f=true;i=-1;z='0';while(++i<n.length){s+=' ';if(t(c+=n[i])>=t(d)){q+=r=Math.floor(t(c)/t(d));o+=(!f?p(c)+w:e)+p(''+r*t(d))+w+p(a(c,'-'))+w;c=t(c)%t(d);f=false}else if(!f){q+=z;}c=(c==0)?e:e+c}return p(!q?z:q)+w+p(a(n,'-'))+w+d+'|'+n+w+o+(q?p(c):e)}

HINWEIS: So verlockend es auch durch den Austausch ein paar Zeichen rasieren sieht c=(c==0)?mit c=!c?, es ist nicht verwendbar , da es verursacht punktbezogenen Bugs schwimmen.

http://jsfiddle.net/nLzYW/9/

Beispielausführung:

document.writeln("<pre>");
document.writeln(d("1234","56"));
document.writeln();
document.writeln(d("1002012","12"));
document.writeln();
document.writeln(d("0","35"));
document.writeln();
document.writeln(d("123000123000123","123"));
document.writeln("</pre>");

Edit 1 : Kleinere Fehlerbehebungen, zahlreiche Code-Optimierungen.

Edit 2 : Fehler behoben, bei dem 1/7 zusätzliche Ausgabe generiert.

mellamokb
quelle
Das Testskript ergab ein Problem. d(1,7)(und ähnliche Tests) Wiederholen Sie den Nenner, anstatt nichts zu drucken. Dies ist falsch, da diese Zahl die Quotientenziffer multipliziert mit dem Nenner sein sollte, der Null ist.
Joey Adams
Alle Tests bestehen jetzt.
Joey Adams
1

Javascript: (372)

function g(a){for(var c="",e=0;e<a;e++)c=" "+c;return c}function i(a,c){for(var e=a+"/"+c+"\\",j=(""+c).split(""),k="",d=0,b=0;b<j.length;b++){d*=10;d+=parseInt(j[b],10);var f=d>9?b-1:b,h=0;h=Math.floor(d/a);d%=a;f=g(f+a.toString().split("").length);f+=h*a+"\n"+g(b+a.toString().split("").length)+"--\n"+g(b+a.toString().split("").length)+d+"\n";k+=f;e+=h}return e+"\n"+k}

Aufruf mit i (Teiler, Zahl). Codegolfed JS: http://jsfiddle.net/puckipedia/EP464/ Ungolfed (niederländisch) JS: http://jsfiddle.net/puckipedia/M82VM/

Gibt die lange Division zurück (im holländischen Format, wie ich es gelernt habe):

5/25\05
 0
 --
 2
 25
  --
  0

Testfall:

document.write("<pre>"+i(5,25)+"</pre>");
document.write("<pre>"+i(7,65669726752476)+"</pre>");
puckipedia
quelle
Hey, das ist nicht das Gleiche wie erforderlich!
Oleh Prypin
@BlaXpirit Ich weiß, ich habe es so gelernt.
Puckipedia
Interessant. Obwohl @BlaXpirit sagt, folgt es nicht der Spezifikation. Die Spezifikation soll ein fairer Vergleichsstandard für die Bestimmung der Effizienz von Code-Golf-Code sein, sodass Sie die Spezifikation nicht willkürlich ändern können, auch wenn Sie nicht mit dem Ausgabeformat einverstanden sind :)
mellamokb