Write a program that visualizes long division with ASCII art. Input consists of two integers, a numerator and a denominator, using the input format of your choice.
Examples:
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
Rules:
- Use of the programming language's division operator is allowed.
- Use of big integer support is also allowed.
- For consistency:
- If the quotient is zero, print a single zero at the end of the diving board.
- If the remainder is zero, do not print it.
- Do not print leading zeros on any numbers.
- Excess newlines at the end and trailing spaces to the right are allowed.
- Solution with the fewest characters wins.
Limits:
- 0 <= numerator <= 1072 - 1
- 1 <= denominator <= 9999999
This implies that the output will never be wider than 80 columns.
Test suite and sample implementation:
You can use long-division.c (gist) to test your program. It is actually a bash script with a C program inside. Tweak it to invoke your program in the test suite. Look at the C code at the bottom to see the reference implementation. Please let me know if there are any problems with the sample program or test suite.
$ ./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!
Edit: By request, I put the test suite input and expected output into text files (gist). Sample usage (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
The weird sed commands filter out trailing newlines and spaces from the program output.
-
4\$\begingroup\$ I think the output is a bit biased towards the English-speaking golfing audience: en.wikipedia.org/wiki/… \$\endgroup\$hallvabo– hallvabo2011年03月15日 11:23:28 +00:00Commented Mar 15, 2011 at 11:23
5 Answers 5
Python 3, (削除) 284 (削除ここまで) 257 characters
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
Usage: python3 div.py
Input: from keyboard
test.py
import sys
sys.stdin=open('input'); sys.stdout=open('output','w')
for line in open('input'): exec(open('div.py').read())
output matches expected
Versions:
1. 284
2. 257: s,z,f=0,0,0
→s=z=f=0
; z and f
→z*f
; better looping; removed a few newlines.
-
3\$\begingroup\$ you may try ideone for python3 and input - ideone.com/clone/ZZyzu \$\endgroup\$YOU– YOU2011年04月04日 04:28:29 +00:00Commented Apr 4, 2011 at 4:28
Haskell, 320 characters
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
Passes all tests. While is this pretty golf'd -- I think there is still yet more to be done here...
- Edit: (344 -> 339) delay
read
calls, which reduces need to callshow
, enough that abbreviatingshow
ass
isn't worth it. - Edit: (339 -> 320) rewrote string field formatting functions
-
\$\begingroup\$ Neat! I did a Haskell solution with 344 characters, but didn't post it. Also, I didn't know you could use Unicode symbols for operators (without
-XUnicodeSyntax
). \$\endgroup\$Joey Adams– Joey Adams2011年04月05日 17:00:35 +00:00Commented Apr 5, 2011 at 17:00
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)}
NOTE: As tempting as it looks to shave off a few chars by replacing c=(c==0)?
with c=!c?
, it is not usable because it causes floating point-related bugs.
Sample Execution:
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: Minor bug fixes, numerous code optimizations.
Edit 2: Fix bug with 1/7 generating extra output.
-
\$\begingroup\$ 314 bytes \$\endgroup\$user100411– user1004112021年04月07日 11:21:18 +00:00Commented Apr 7, 2021 at 11:21
AWK, 422 bytes
I think it took me over a week to solve this problem.
function l(x){return length(x)}{P=9(d=2ドル);gsub(".",FS,P);N=l(L=n=1ドル);gsub(".","-",L);O(0,q=int(1ドル/2ドル));Q=l(q);print P L RS d"|"n}function O(i,x){printf"%"l(d)+N-Q+1+i"d\n",x}m=substr(q,1,1)*d{for(i=1;i<=Q;){O(i,m);print P substr(L,1,N-Q+1);for(_=l(j=n)-l(n-=m*10**(Q-i));_--;)P=P FS;if(!n)exit;match(q,".0*");i+=R=RLENGTH;sub(".{"R"}",E,q);b=q+0?substr(n,1,M=l(m=substr(q,1,1)*d)):n;if(b<m)b=substr(n,1,M+1);O(i-(i>Q),b)}}
Usage
- Input is given from STDIN, as single line.
- Two natural numbers are on same line.
- Output is returned to STDOUT.
- This program does never handle overflow; fails on huge values.
- This program does not handle multiple lines of input correctly; only the first line is handled correctly.
Formatted
function l(x){
return length(x)}
{
P=9(d=2ドル);gsub(".",FS,P);
N=l(L=n=1ドル);gsub(".","-",L);
O(0,q=int(1ドル/2ドル));
Q=l(q);
print P L RS d"|"n}
function O(i,x){
printf"%"l(d)+N-Q+1+i"d\n",x}
m=substr(q,1,1)*d{
for(i=1;i<=Q;){
O(i,m);
print P substr(L,1,N-Q+1);
for(_=l(j=n)-l(n-=m*10**(Q-i));_--;)
P=P FS;
if(!n)
exit;
match(q,".0*");
i+=R=RLENGTH;
sub(".{"R"}",E,q);
b=q+0?substr(n,1,M=l(m=substr(q,1,1)*d)):n;
if(b<m)
b=substr(n,1,M+1);
O(i-(i>Q),b)}}
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}
Invoke by using i(divider,number). Codegolfed JS: http://jsfiddle.net/puckipedia/EP464/ Ungolfed (dutch) JS: http://jsfiddle.net/puckipedia/M82VM/
Returns the long division (in dutch format as i learned it):
5/2505円
0
--
2
25
--
0
Testcase:
document.write("<pre>"+i(5,25)+"</pre>");
document.write("<pre>"+i(7,65669726752476)+"</pre>");
-
1\$\begingroup\$ Interesting. Though as @BlaXpirit says, it doesn't follow the spec. The spec is intended to be a fair standard of comparison for determining efficiency of code-golfed code, so you can't arbitrarily change the spec even if you don't agree with the output format :) \$\endgroup\$mellamokb– mellamokb2011年04月04日 16:40:43 +00:00Commented Apr 4, 2011 at 16:40
Explore related questions
See similar questions with these tags.