language agnostic - Code Golf: dibujar ascii estrellas del arte
language-agnostic code-golf (6)
OCaml, 659 caracteres (wc -c).
Utiliza el algoritmo clásico de Bresenham para dibujar las líneas, recursivas por diversión. Guardar como stars.ml
y ejecutar con echo 5 2 20 | ocaml stars.ml
echo 5 2 20 | ocaml stars.ml
.
let pl b x y=b.(x).[y]<-''x''
let ln b x0 y0 x1 y1 =
let rec h p x0 y0 x1 y1 =
if x0>x1 then h p x1 y1 x0 y0
else(
let dx,dy,ys=x1-x0,abs(y1-y0),if y0<y1 then 1 else -1 in
let rec k x y e=
if x<=x1 then(
p y x;
if e<dy then k(x+1)(y+ys)(e-dy+dx)
else k(x+1)y(e-dy)
)in
k x0 y0(dx/2)
)in
if abs(y1-y0)>abs(x1-x0)then
h(fun x y->pl b y x)y0 x0 y1 x1
else h(pl b)x0 y0 x1 y1
let f=float
let g n s d=
let b=Array.init d(fun _->String.make d '' '')in
let r=f(d/2)-.0.1 in
let k h i=int_of_float(r+.r*.h(6.2831853*.(f(i mod n)/.(f n))))in
let x,y=k cos,k sin in
for i=0 to n do ln b(x i)(y i)(x(i+s))(y(i+s))done;Array.iter print_endline b
let()=Scanf.scanf"%d %d %d"g
Salidas
x x x
xx xxx xx
xx x x xxx xx x
x x x xxxxx x x x x
xx x x xxxxxx xx x x x xxx
xxxxx x x xxx x x x xxx x x x x
x xxxx x x x xx xxxxxxx xx x
x x xxx x x xx x xxxxx x
x x x xxxx x x x x x xx xxxxxx
x x xx xx x x xxx x xxx
x x xxx x x x xxx x xxxx
x x xxx xx xx x xx xxxx
x x xxxx x x xx x xxxxxx x
x xxx x x x x x xxxxx x xx x
xxxx x x xxx x x x xx x x x x
xx x x xxxxxx x x x x xxx
x x x xxxxx x x x x
xx x xx xxx xx x
xx x x xx
x x x
Como esta semana nadie ha publicado un desafío de código de golf, lo intentaré. Lo hago para que puedas hacer algo más que jugar con espadas durante esos largos ciclos de compilación.
El reto:
Dibuja estrellas de arte ASCII, dando tres números en la entrada estándar (número de picos, tipo de estrella (la estrella se dibuja uniendo los vértices que están n vértices separados) y el diámetro de la estrella). Ejemplos:
Input: Input: Input:
5 2 20 7 2 20 7 3 20
Output: Output: Output:
x x x
xx xx x
xx x xx xx xx x
x x x xxxx x xx xx
xx x x xxxxx x x x x xxx
xxxx x x xxxx x x x x x x
x xxx x xx x xx xxx x x x
x x xxxx x x xx x xxxxx xx x
x x xxx x x x x xx xxxxxx
x x x xxx x x x x x xx xxxxxx
x x xx x x x x x x xxx
x x x xxx x x x x xx xxxxxx
x x xxx x x x x xx xxxxxx
x x xxxx x x xx x xxxxx xx x
x xxx x xx x xx xxx x x x
xxxx x x xxxx x x x x x x
xx x x xxxxx x x x x xxx
x x x xxxx x xx xx
xx x xx xx xx x
xx x x x
x x x
Como rastrillar correctamente las líneas puede ser un PITA para un desafío de golf de código, dejaré algo de margen, pero no demasiado. Más ejemplos:
Suficientemente bueno:
x x x x
xx xx x x
x x x x
x xx xx x x x
x x x
x x x
xxx xxx x x
x x xxxxxxxxxxxxxxxxxxxxx
x x xx x x xx
xx x x xx xx x x xx
x x xxx xxx
xxxxxxxxxxxxxxxxxxxxx xxxxx
x x x xx xx x
x xx xx x
xxx xxx
x x xx x x xx
x
x
No lo corta:
x xx xx
xx x x
xx x x
x x xx xx
xx x x x x
xxxx x x x xx xx x
x xxxx x x
x xxxx x x x
x x xxx xxx xxx
xx x xxxxxx x x
xx x xxxxxx x x
xx xxx xx x x xx
x x xxx x x x
x xxx x xxxxxxxxxxxxxxxxxxxxx
xxx x x x x
xx x x
x x
x x x x
x x
xx
x
Lack of precission Lack of clipping
¡Que te diviertas!
C #: 555 428 caracteres
using System.Drawing;class P{static void Main(string[]a){int p=int.Parse(a[0]),i=int.Parse(a[1]),l=int.Parse(a[2]),n;var o=System.Console.Out;var b=new Bitmap(l*4/3,l*4/3);var g=Graphics.FromImage(b);g.TranslateTransform(l/8,l/3);for(n=0;n<p;n++){g.DrawLine(Pens.Red,0,0,l,0);g.TranslateTransform(l,0);g.RotateTransform(360*i/p);}for(i=0;i<b.Height;i++,o.WriteLine())for(p=0;p<b.Width;p++)o.Write(b.GetPixel(p,i).A>0?"#":" ");}}
Estrellas 5 2 20
#
# #
# #
# #
# #
# #
#####################
## # # ##
# # # #
# # # #
## ##
## ##
# # # #
# ### #
# # # #
# ## ## #
# # # #
## ##
# #
Javascript (basado en la solución de python de Isc), 598 591 586 559 bytes (usado con rhino shell: guardar como ''stars.js'', ejecutar con ''rhino stars.js 7 2 20''):
for(var a=Math,b=parseInt,c=a.floor,d=a.abs,e=arguments,f=b(e[0]),g=b(e[1]),h=b(e[2]),i=[],j=0;j<(h+1)*h;j++)i.push((j+1)%(h+1)?" ":"/n");function k(w,x){i[x*(h+1)+w]="x"}var l=(h-1)/2,m=[];for(j=0;j<f;j++)m.push([c(l*a.cos(a.PI*2/f*j)+h/2),c(l*a.sin(a.PI*2/f*j)+h/2)]);
for(j=0;j<f;j++){var n=m[j][0],o=m[j][1],p=m[(j+g)%f][0],q=m[(j+g)%f][1],r=void 0,s=void 0;if(r=d(q-o)>d(p-n)){s=n;n=o;o=s;s=p;p=q;q=s}if(n>p){s=n;n=p;p=s;s=o;o=q;q=s}for(var t=p-n,u=0,v=d(q-o)/t,y=o<q?1:-1,z=o,A=n;A<=p;A++){r?k(z,A):k(A,z);u+=v;if(u>=0.5){z+=y;u-=1}}}print(i.join(""));
Salida:
x xx xx x x xx x x xxxx x x x xxx x x x xxx x x xxx xx x xxx xx x xx x x x xxxx x x xxx x xxx x xxxxx x x xx x x x x xx xx x x xx x x xxx x xxxx x xxxxx x x xxx x x x x x xx x x x x x xxx x x x x x x x x x xx x x xx x x x xxx x xxx xxxxx x x x xxxx x x xx xxx xx x x x xx x xx xx x x xx xx x x xx x xxxxxx x x x xxxx x xx xx xxxx xx xx xxxx xx xx xxx xx xx xxxxxx x xxxxxxx x xxxx x x xxx x x xx x x x xx xx xx xx x x x
Código expandido:
var p = parseInt(arguments[0]),
t = parseInt(arguments[1]),
w = parseInt(arguments[2]);
var g = [];
for(var i = 0; i < (w + 1) * w; i++)
g.push((i + 1) % (w + 1) ? '' '' : ''/n'');
function plot(x, y) { g[y * (w + 1) + x] = ''x'';}
function line(x0, y0, x1, y1) {
var steep = Math.abs(y1 - y0) > Math.abs(x1 - x0), temp;
if(steep) {
temp = x0; x0 = y0; y0 = temp;
temp = x1; x1 = y1; y1 = temp;
}
if(x0 > x1) {
temp = x0; x0 = x1; x1 = temp;
temp = y0; y0 = y1; y1 = temp;
}
var deltax = x1 - x0;
var deltay = Math.abs(y1 - y0);
var error = 0;
var deltaerr = deltay / deltax;
var ystep
var y = y0;
if(y0 < y1) ystep = 1; else ystep = -1;
for(var x = x0; x <= x1; x++) {
if(steep) plot(y,x); else plot(x,y);
error = error + deltaerr;
if(error >= 0.5) {
y = y + ystep;
error = error - 1.0;
}
}
}
var r = (w-1)/2, points = [];
for(var i = 0; i < p; i++) {
points.push([
Math.floor(r * Math.cos(Math.PI * 2 / p * i) + w/2),
Math.floor(r * Math.sin(Math.PI * 2 / p * i) + w/2)
]);
}
for(var i = 0; i < p; i++) {
line(points[i][0], points[i][1], points[((i + t) % p)][0], points[((i + t) % p)][1]);
}
print(g.join(''''));
VBScript, 584 511 482 bytes
También utilicé el algoritmo de Bresenham para líneas.
g=Split(WScript.StdIn.ReadAll):t=g(1):d=g(2):ReDim r(d*d)
For i=0 To d*d:r(i)=" ":Next
c=1.57:u=(d-1)/2:b=c*4/g(0):For i=1 To g(0)
Z n:x=g:Z n+c:y=g:Z n-b*t:f=g:Z n-b*t+c:n=n+b
s=Abs(g-y)>Abs(f-x):If s Then W x,y:W f,g
If x>f Then W x,f:W y,g
p=f-x:q=Abs(g-y):h=p/2:v=(y>g)*2+1
For x=x To f:r((s+1)*(y*d+x)-s*(x*d+y))="x"
h=h-q:If h<0 Then y=y+v:h=h+p
Next:Next:For i=0 To d:WScript.Echo Mid(Join(r,""),i*d+1,d):Next
Sub W(a,b):e=a:a=b:b=e:End Sub
Sub Z(e):g=Int(u*Cos(e)+u):End Sub
Salida:
x x x
xx xx x
xx x xx xxx xx x
x x x xxxx x xx xx
xx x x xxxxx x x x x xx
xxxx x x xxx x x x xx x x xx x
x xxx x x x xx xxxxxx x x
x x xxx x x xx x xxxx x
x x xxx x x x x xx xx xxx
xx x xxx x x x xx xx xxxx
xx x xx x x x xx xx xxx
x x x xxxx x x x x xx xx xxxxxx
x x xxx x x xxx x xxxxxxx
x xxx x x x x x xxxx x x
xxxxx x x xxx x xx xxx x x xx x
xx x x xxxxx xx x x x xx
x x x xxxx x xx xx
xx x x xxx xx x
xx xxx x
x x x
Código expandido:
Dim PI, args, output, i
PI = 4 * Atn(1)
args = Split(WScript.StdIn.ReadAll, " ")
output = Join(Star(args(0), args(1), args(2)), vbNullString)
For i = 1 To Len(output) Step args(2)
WScript.Echo Mid(output, i, args(2))
Next
Function Star(spikes, star_type, diameter)
Dim result(), i, vertexes(), angle, radius, p1, p2
ReDim result(diameter * diameter - 1)
ReDim vertexes(spikes - 1)
For i = 0 To UBound(result)
result(i) = " "
Next
radius = (diameter - 1) / 2
For i = 0 To UBound(vertexes)
vertexes(i) = Array(CLng(radius * Cos(angle) + radius), _
CLng(radius * Sin(angle) + radius))
angle = angle - (2 * PI / spikes)
Next
For i = 0 To UBound(vertexes)
p1 = vertexes(i)
p2 = vertexes((i + star_type) Mod spikes)
DrawLine p1(0), p2(0), p1(1), p2(1), result, diameter
Next
Star = result
End Function
Sub DrawLine(ByVal x0, ByVal x1, ByVal y0, ByVal y1, arr, diameter)
Dim steep, deltax, deltay, error, ystep
steep = Abs(y1 - y0) > Abs(x1 - x0)
If steep Then
Swap x0, y0
Swap x1, y1
End If
If x0 > x1 Then
Swap x0, x1
Swap y0, y1
End If
deltax = x1 - x0
deltay = Abs(y1 - y0)
error = deltax / 2
If y0 < y1 Then ystep = 1 Else ystep = -1
For x0 = x0 To x1
If steep Then
arr(x0 * diameter + y0) = "x"
Else
arr(y0 * diameter + x0) = "x"
End If
error = error - deltay
If error < 0 Then
y0 = y0 + ystep
error = error + deltax
End If
Next
End Sub
Function Swap(a, b)
Dim temp
temp = a
a = b
b = temp
End Function
Mi primer intento de código de golf ...
Python - 550 533 507 484 451 437 caracteres
Guardar como k.py
Ejecutar como python k.py 5 2 20
import sys,math as m
A=abs;R=range;X=round
p,t,w=map(int,sys.argv[1:])
G=[['' '']*-~w for i in R(w+1)]
def L(a,b,c,d):
s=A(d-b)>A(c-a)
if s:a,b,c,d=b,a,d,c
if a>c:a,b,c,d=c,d,a,b
f=c-a;e=f/2;y=int(X(b));x=int(X(a))
while x<X(c):
e-=A(d-b);p,q=((x,y),(y,x))[s];G[p][q]=''x'';x+=1
if e<0:y+=(-1,1)[y<d];e+=f
r=w/2;k=m.pi*2/p
s=[(m.sin(k*i)*r+r,m.cos(k*i)*r+r)for i in R(p+t)]
for i in R(p):L(*(s[i]+s[i+t]))
for i in G:print''''.join(i)
(Se pueden guardar 2 caracteres más reemplazando la sangría de segundo nivel por pestañas ...)
Versión expandida disponible aquí: http://gist.github.com/591485
Ejemplo de salida:
x x x
xx xx x
xx x xx x xx x
x x x xxxxx xx xx
xx x x x xxxx x x x x xxx
xxxx x x xxxx x x x x x x
x xxx x xxx x xx xxx x x x
x x xxxx x x xx x xxxxx xx x
x x xxx x x x x xx xxxxxx
x x xxx x x x x x xx xxxxx
x x x x x x x xx xxx
x x x xxx x x x x xx xxxxx
x x xxx x x x x xx xxxx x
x xxxxx x x xx x xxxxx xx x
x xxx x xxx x xx xxx x xx x
x xxx x x xxxx x x x x x x
xx x x x xxxx x x xx xx x
x x x xxxxx xx xx
xx x xx x
x x x x
x
Ruby - 323 276 304 297
a,b,c=gets.split.map &:to_i
o=(0..c).map{'' ''*c}
m=(1..a).map{|i|r=2*h=Math::PI*i/a
[(1+Math.sin(r))*c/2+0.5,(1+Math.cos(r))*c/2]}
a.times{|n|j,i,x,y=*m[n],*m[n-b]
j,x,i,y=i,y,j,x if k=((i-y)/(j-x))**2>1
s,z=[x,j].sort
s.to_i.upto(z){|m|t=i+(m-j)*(i-y)/(j-x)
k ?(o[t][m]=''x''):(o[m][t]=''x'')}}
puts o
x xx x xx
x x x x x x
xx x x xx xx x x x
x x x xxxx x xx xx xxxxxxxxxxxxxxxx
xxx x x xxxxx xx x x x xx x x x x
x xxx x x xxxxx x x x x x x x x x x x
x xxx x xx x xx xxxx x xxx x x x xx
x x xxxx x x x x xxxxxx x xx x
x x xxx x x xxx x x xxxxx x xx
x x x xxx xx x x x xx x xxxxx xx x x
xx x xx xx x x xx x xxxx x x x
xx x xxx xx x x x xx x xxxx xx x x
x x xxx xx xxx x x xxxxx x xx
x x xxxx x x x x xxxxxxx x xx x
x xxx x xx x xx xxxx x xxx x x x xx
x xxx x x xxxxx x x x x x xx x x x x
xxx x x x xxxx xx x x x xx x x x x
x x x xxxx x x x x xxxxxxxxxxxxxxxx
x x x x xx xx x x x
xx x x xx x x
x xx x x