language agnostic - Code Golf: Telarañas
language-agnostic code-golf (15)
El reto
El código más corto por carácter cuenta para dar salida a una telaraña con anillos iguales a la entrada del usuario.
Se inicia una telaraña reconstruyendo el anillo central:
/_|_/
_/ /_
/___/
/ | /
Luego agregando anillos iguales a la cantidad ingresada por el usuario. Un anillo es otro nivel de un "círculo de araña" hecho de / / |
y _
, y envuelve el círculo central.
La entrada siempre está garantizada como un único entero positivo.
Casos de prueba
Input
1
Output
/__|__/
//_|_//
_/_/ /_/_
/ /___/ /
//_|_//
/ | /
Input
4
Output
/_____|_____/
//____|____//
/ //___|___// /
/ / //__|__// / /
/ / / //_|_// / / /
_/_/_/_/_/ /_/_/_/_/_
/ / / / /___/ / / / /
/ / / //_|_// / / /
/ / //__|__// / /
/ //___|___// /
//____|____//
/ | /
Input:
7
Output:
/________|________/
//_______|_______//
/ //______|______// /
/ / //_____|_____// / /
/ / / //____|____// / / /
/ / / / //___|___// / / / /
/ / / / / //__|__// / / / / /
/ / / / / / //_|_// / / / / / /
_/_/_/_/_/_/_/_/ /_/_/_/_/_/_/_/_
/ / / / / / / /___/ / / / / / / /
/ / / / / / //_|_// / / / / / /
/ / / / / //__|__// / / / / /
/ / / / //___|___// / / / /
/ / / //____|____// / / /
/ / //_____|_____// / /
/ //______|______// /
//_______|_______//
/ | /
El recuento de códigos incluye entrada / salida (es decir, programa completo).
C, 573 caracteres
Obviamente, ni siquiera está en ejecución con respecto al recuento de caracteres. El número 573 es solo el tamaño del archivo en mi máquina de Windows, por lo que probablemente cuente unos ctrl-M. Por otro lado, tal vez 573 está subestimando, ya que incurrí en la ira del compilador desechando todos los #includes para ahorrar espacio, ¡las advertencias serían condenadas!
Pero bueno, esta es la primera vez que intento uno de estos, y sin duda será una buena práctica tratar de volver a expresarlo en algo más compacto.
#define B puts("");
#define K ''//'+''/''
#define F ''_''+'' ''
#define P(s) putchar(s);
#define I int
c(I s,I f){if(s){P(f)c(s-1,f);P(f)}else P(''|'')}
w(I lw,I s,I k,I f){if(s){P('' '')P(k)w(lw,s-1,k,f);P(K-k)P('' '')}else{P(K-k)c(1+lw,f);P(k)}}
h(I g,I s,I k,I f){I i;for(i=-1;i<g;++i)P('' '')w(g,s,k,f);}
t(I g,I s){if(s)t(g+1,s-1);h(g,s,''/'',''_'');B}
b(I g,I s){h(g,s,''//',s?''_'':'' '');B;if(s)b(g+1,s-1);}
m(I s,I k,I f){if(s){P(f)P(k)m(s-1,k,f);P(K-k)P(f)}else{P(F-f)P(F-f)P(F-f)}}
main(I ac,char*av[]){I s;s=atoi(av[1]);t(0,s);m(1+s,''/'',''_'');B;m(1+s,''//','' '');B;b(0,s);}
Golfscript - 124 caracteres
¡Todo espacio en blanco es significativo! Si accidentalmente agrega una nueva línea al final, habrá un _
adicional al final de la salida
~):@,{@/:&-:0'' '': *& ''/'':/+*''//':~''_'':
0*.''|'':|//~ +&*n}%
/+@* ~
+@*n ~+@*
@/ +*n@,{):& *@&-:( ~+*/[
](!=&*.|/~/ +(*n}%
Golfscript - 129 caracteres
~):@,{@/:&-:0'' '': *&'' /''*''//':~''_'':
0*.''|''/'/''~ +&*n}%''_/''@* ''/_''@*n ~+@*
@''/ ''*n@,{):& *@&-:( ~+*''/''[
](!=&*.''|''/~''/ ''(*n}%
Golfscript - 133 caracteres
~):@,{@/:&-:0'' '': *&'' /''*''//':~''_'':
0*.''|''/'/''~ +&*n}%''_/''@*3 *''/_''@*n'' //'@*3
*@''/ ''*n@,{):& *@&-:( ~+*''/''''_ ''1/(!=&*.''|''/~''/ ''(*n}%
Perl 264 caracteres
acortado al alinear las subrutinas.
perl -E''$"="";($i=<>)++;@r=map{$p=$i-$_;@d=(" "x$_,(" ","//")x$p,"/","_"x$_);($d="@d")=~y:///:///:;@d=reverse@d;$d.="|@d"}1..$i;say for reverse@r;$_=$r[0];y: _|:_ :;s:.(.*)//.*/(.*).:$1_/ //_$2:;say;y: _///:_ ///:;say;$r[-1]=~y:_: :;say for grep{y:///:///:}@r;''
Ampliado para mejorar la legibilidad.
perl -E''
$"="";
($i=<>)++;
@r=map{
$p=$i-$_;
@d=(
" "x$_,
(" ","//")x$p,
"/",
"_"x$_
);
($d="@d")=~y:///:///:;
@d=reverse@d;
$d.="|@d"
}1..$i;
say for reverse@r;
$_=$r[0];
y: _|:_ :;
s:.(.*)//.*/(.*).:$1_/ //_$2:;
say;
y: _///:_ ///:;
say;
$r[-1]=~y:_: :;
say for grep{y:///:///:}@r;
''
Este es el código antes de que lo minimice:
#! /opt/perl/bin/perl
use 5.10.1;
($i=<>)++;
$"=""; #" # This is to remove the extra spaces for "@d"
sub d(){
$p=$i-$_;
" "x$_,(" ","//")x$p,"/","_"x$_
}
sub D(){
@d=d;
($d="@d")=~y:///:///:; # swap ''/' for ''/''
@d=reverse@d;
$d.="|@d"
}
@r = map{D}1..$i;
say for reverse@r; # print preceding lines
# this section prints the middle two lines
$_=$r[0];
y: _|:_ :;
s:.(.*)//.*/(.*).:$1_/ //_$2:;
say;
y: _///:_ ///:;
say;
$r[-1]=~y:_: :; # remove ''_'' from last line
say for grep{y:///:///:}@r; # print following lines
Python: 240 caracteres
Nada demasiado complicado aquí; simplemente imprime línea por línea - 298 280 271 266 265 261 260 254 240 caracteres (ignora los últimos 2 saltos de línea)
u,b,f,s,a=''_// |''
m=input()+1
print''/n''.join([(m-x)*s+x*'' /''+b+(m-x)*u+a+(m-x)*u+f+x*''/ ''for x in
range(0,m)]+[''_/''*m+s*3+''/_''*m+''/n''+(s+b)*m+u*3+''/ ''*m]+[x*s+(m-x)*
'' //'+f+x*u+a+x*u+b+(m-x)*''/ ''for x in range(1,m)] + [s*m+f+s*m+a+s*m+b])
Ruby1.9 - 181 caracteres
n=gets.to_i+1;s='' ''
a=0.upto(n-1).map{|i|s*(j=n-i)+'' /''*i+?//+?_*j+''|''+?_*j+?/+''/ ''*i+s*j}
d=a.reverse.map{|x|x.reverse};d[-1].tr!?_,s
puts a,''_/''*n+s*3+''/_''*n,'' //'*n+?_*3+''/ ''*n,d
Ruby1.8 - 185 caracteres
Algunas mejoras de JRL
n=gets.to_i+1;s='' ''
u=''_'';a=0.upto(n-1).map{|i|s*(j=n-i)+'' /''*i+''//'+u*j+''|''+u*j+''/''+''/ ''*i+s*j}
d=a.reverse.map{|x|x.reverse}
d[-1].tr!u,s;puts a,''_/''*n+s*3+''/_''*n,'' //'*n+u*3+''/ ''*n,d
Ruby - 207 caracteres
Ruby parece tener algunas reglas peculiares sobre la "/"
n=eval(gets)+1
b,f,p,u,s=''//|_ ''.split""
a=0.upto(n-1).map{|i|s*(j=n-i)+'' /''*i+b+u*j+"|"+u*j+f+"// "*i+s*j}
puts a,''_/''*n+s*3+''/_''*n,'' //'*n+u*3+''/ ''*n,a[1..-1].reverse.map{
|x|x.reverse},a[0].reverse.tr(u,s)
Vb.net, Windows console, Infer, Strict, Explicit ON.
Microsoft Word dice 442 caracteres sin espacio
Podría ser posible reducirlo más, pero esta es mi última actualización ( intento # 2 )
Module z
Sub Main()
Dim i = CInt(Console.ReadLine), j = i + 1, h = j * 2 + 1, w = h * 2, z = "_", b = " "
For y = 0 To h
For x = 0 To w
Dim l = (x + y Mod 2 + i Mod 2) Mod 2, u = j + y, e = j - y, k = h + e, o = x = h Or x = h - 1
Console.Write(If(x = h, If(y = j, b, If(y = j + 1, z, "|")), "") & If(x = w, vbLf, If(y = j, If(x Mod 2 = 0 = (x < h), If(o, b, z), If(x < h, "/", "/")), If(x < k And x > u Or (x < u And x > k Or o) And y < h, z, If(x = k Or (x < u And y < j And x > e Or x > u And y > j And x < w + e) And l = 0, "/", If(x = u Or (x > k And y < j And x < h + u Or x < k And y > j And x > y - j - 1) And l = 1, "/", b))))))
Next
Next
End Sub
End Module
Lua, 290
n=...s=string r=s.reverse g=s.gsub a="//|/"j=(" /"):rep(n+1)..a..("// "):rep(n+1) k=j o=k l=n*4+7 for i=1,n+1 do k=g(k,"^(.- )/(.-)|(.*)//(.-)$","%1%2_|_%3%4")o=k..o end o=o..r(o)print((g(g(g(g(r(g(o:sub(1,l),"_"," ")..o:sub(l+1)),j,g(j," ","_")),("."):rep(l),"%1/n"),a," "),r(a),"___")))
Perl, 164 caracteres
195 184 171 167 164
print@o=((map{$z=_ x($x=1+$N-$_);$"x$x." /"x$_."//$z|$z/".''/ ''x$_.$/}0..($N=<>)),
"_/"x++$N." ".''/_''x$N.$/);
y''///'//'',@o||y#_# #,$t++||y#_ # _#,print while$_=pop@o
La primera declaración imprime la mitad superior de la telaraña. La segunda declaración usa operaciones de transliteración para crear un reflejo de la mitad superior.
Este próximo pesa más cerca de 314 caracteres (de código productivo), pero está más en el espíritu de la temporada.
; "
Tr Ic
K| |t
Re aT
", "H
av e
A: -
)H AL LO W
ee N" ," En
jo y_ Yo ur
_ C&& y"; ##
&I (); $N= 1+
<>; $,= $/;@O =(( map
$" x($ X=$N-$_). ${ f}x$_.$
B.${U}x$X.$P.${U}x$X.$
F.${b}x$_,0..$N-1),${g}x$N.(${S}
x3).${c}x$N);sub I{($F,$B,$U, $P)
=qw (/ // _ |);; ${
S}= " ";$f=$S.$F;$g=$ U.
$F ;$b=$B.$S;$c=$B.${U};}@{ P}=
@{ O}; while($_=pop@{P} ){ @{
P} || y:_: :;$spooky++ || 0|
0 || y@_ @ _@;y:/:8:; ; ;
; ;; y://:/:;y:8://:; @O =
( @O ,$_);}print@O; q{
Do !Discuss:Rel ig
io n,Politi cs
,& &T
heG rea
tP ump
ki n}
Punta de sombrero para http://www.ascii-art.de/ascii/s/spider.txt
Acme::AsciiArtinator el código en forma de araña a mano, pero vea el módulo Acme::AsciiArtinator en CPAN para obtener ayuda con la automatización (o al menos semi-automatización) de la tarea.
Perl: 161 caracteres
Tenga en cuenta que este código incluye la web de inicio en la fuente. (La doble barra invertida al final es una pena. Una versión anterior no tenía eso).
$_=''
/_|_/
_/ /_
/___/
/_|_//';
for$x(1..<>){
s|(./S).*([///].)|$1$&$2|g;
s|//(.*)/| //_$1_/$` /$&// |;
s|(/s+)/K/(.*).$| //$&/$1 /_$2_//|
}
s|_(?=.*$)| |g;
print
El espacio en blanco dentro de $_
es significativo (por supuesto), pero el resto no lo es. Si tiene una sugerencia menor que mejora esto, siéntase libre de simplemente editar mi código. ¡Por ejemplo, Kinopiko ha afeitado 6 personajes!
Dependiendo de cómo cuente los interruptores de línea de comando, esto podría ser más corto (154 por las reglas de golf Perl habituales si puedo contar correctamente):
#!perl -ap
$_=''
/_|_/
_/ /_
/___/
/_|_//';
s|(./S).*([///].)|$1$&$2|g,
s|/S(.*).| //_$1_/$` /$&// |,
s|(/s+)/K/(.*).$| //$&/$1 /_$2_//|while$F[0]--;
s|_(?=.*$)| |g
Python - 212 caracteres
n=input()+1;b,f,p,u,s=''//|_ ''
a=[s*(n-i)+'' /''*i+b+u*(n-i)+p+u*(n-i)+f+''/ ''*i+s*(n-i)for
i in range(n)]
print"/n".join(a+[''_/''*n+s*3+''/_''*n,'' //'*n+u*3+''/ ''*n]+[x[::-1]for
x in a[:0:-1]]+[a[0][::-1].replace(u,s)])
Python, 340 - 309 - 269 - 250 caracteres
Todavía hay margen de mejora, creo.
s=input()+1
f,b="/ ","//"
r=range(s)
for i in r:w="_"*(s-i);print" "*(s+(i>=1)-i)+(f*i)[:-1]+b+w+"|"+w+"/"+"/ "*i
print"_/"*s+" "*3+"/_"*s+"/n"+" //"*s+"_"*3+f*s
for i in r[::-1]:u="_ "[i<1]*(s-i);print" "*(s-i+(i>=1))+("/ "*i)[:-1]+"/"+u+"|"+u+b+f*i
-
Python (versión alternativa), de 250 a 246 caracteres
s=input()+1;r=range(s);c="/","//";y="/ ","// "
def o(i,r):u="_ "[i<1 and r]*(s-i);print" "*(s+(i>=1)-i)+(y[r]*i)[:-1]+c[r<1]+u+"|"+u+c[r]+(y[r<1]*i)[:-1]
for i in r:o(i,0)
print"_/"*s+" "*3+"/_"*s+"/n"+" //"*s+"_"*3+"/ "*s
for i in r[::-1]:o(i,1)
Ruby 1.8 , 179
Corre con ruby -n
n=$_.to_i+1
u,s,c=%w{_ / / //}
z=(1..n).map{|i|k=n-i
s*i+c*k+''/''+u*i+''|''+u*i+"//"+''/ ''*k+s*i}
y=z.reverse.map{|a|a.reverse}
z[-1].tr!u,s
puts y,''_/''*n+s*3+''/_''*n,c*n+u*3+''/ ''*n,z
En el primer intento a continuación, me pareció una buena idea generar un solo cuadrante (elegí abajo a la izquierda), y luego duplicar dos veces para obtener toda la web. Pero gnibbler obtuvo mejores resultados generando ambos cuadrantes (de la mitad superior) y luego generando en lugar de remendar el área interna. Así que revisé el mío para generar inicialmente el otro cuadrante inferior también, reflejar solo una vez, y también para dejar la fila más interna fuera del espejo, que tipo de converge con la otra entrada.
Ruby, 241
n=$_.to_i+1
m=2*n+1
u,s,b,f=%w{_ / // /}
z=(0..n).map{|i|s*i+(s+b)*(n-i)+(i==0?u:f)+u*i}
q=z.reverse.map{|a|a.tr f+b,b+b+f}
q[n].gsub!'' '',''_''
q[n][m-1]=s
z=(q+z).map{|a|a+''|''+a.reverse.tr(f+b,b+b+f)}
z[n][m]=z[n+1][m]=s
z[m].gsub!u,s
puts z
dc - 262
Una solución "directa" en dc
(OpenBSD). No es un contendiente, pero siempre es divertido. Saltos de línea para "legibilidad"
[lcP1-d0<A]sA?sN[lK32sclAxRlNlK-l1scd0!=ARl3PlKl0sclAxRl9PlKlAxRl4PlNlK-
l2scd0!=AAPR]sW95s0124s9[ /]s1[// ]s292s347s4lN[dsKlWx1-d0<L]dsLx
[//_][ ][_/][lN[rdPr1-d0<L]dsLxRRPlNlLxRR]dsBxAP[/ ][_ _][ //]lBxAP[ //]s1
[/ ]s247s392s41[dsKlWx1+dlN>L]dsLx32s032s9lNsKlWx
muestra de salida
$ dc web.dc
3
/___|___/
//__|__//
/ //_|_// /
_/_/_/ /_/_/_
/ / /_ _/ / /
/ //_|_// /
//__|__//
/ /
Python y Ruby casi iguales *
Preferiría haber continuado el hilo de comentarios que mencioné brevemente Python vs Ruby, pero necesito un formato para hacerlo. Smashery es ciertamente elegante, pero no necesita preocuparse: resulta que Python y Ruby están en una carrera muy reñida por una medida. Volví y comparé Python con Ruby en los ocho campos de golf en los que participé.
Challenge Best Python Best Ruby The Wave 161 99 PEMDAS no python entry (default victory?) Seven Segs 160 175 Banknotes 83 (beat Perl!) 87 Beehive 144 164 RPN (no eval) 111 (157) 80 (107) Cubes 249 233 Webs 212 181 Victories 3 4 (5?)
Así que el problema definitivamente no está resuelto y se volvió más interesante recientemente cuando gnibbler comenzó a ingresar en ambos lados. :-)
*
Solo conté entradas completamente funcionales.
(&)=(++) --9
f 0=[" //_|_/","_/ //_"," //___/"," / | //"] --52
f(n+1)=[s&h&u&"|"&u&g]&w(f n)&[s&g&s&"|"&s&h]where[a,b,c,d,e]=" _///|";[g,h]=["/","//"];y=n+2;[u,s]=[r y b,r y a];p f s n x=let(a,b)=span(/=s)x in a&f b;i=dropWhile(==a);w[]=[];w[x]=[s&h&i(p(map(/x->if x==a then b else x))c d x)&g];w(l:e)|n==y*2-1=x%h:z|n>y=x&" "%" //":z|n==y="_/"%"//_":z|n<y=r(y-n)a&"// "%" /":z where n=length e;z=w e;x=r(n+1-y)a&g;(%)=(&).(&i l) --367
r=replicate --12
main=interact$unlines.f.read --29
Entrada de Haskell con un peso de 469 caracteres. Estoy seguro de que hay mucho margen de mejora.
buena suerte tratando de leerlo :)
aquí hay una versión más legible Aunque ha habido algunos cambios desde esta versión
spider 0=[" //_|_/","_/ //_"," //___/"," / | //"]
spider n=(s++"//"++u++"|"++u++"/"):w m(spider(n-1))++[s++"/"++s++"|"++s++"//"]
where
[a,b,c,d,e]=" _///|"
[m,y]=[y*2,n+1]
x=r y
[u,s]=[x b,x a]
t a b=map(/x->if x==a then b else x)
p f s n x=let(a,b)=span(/=s)x;(c,d)=span(/=n)b in a++f c++d
i=dropWhile(==a)
w _[]=[]
w _[x]=[s++"//"++i(p(t a b)c d x)++"/"]
w(a+1)(l:e) |a==m-1=wrapline x l"//":z
|a>y=wrapline(x++" ")l" //":z
|a==y=wrapline"_/"l"//_":z
|a<y=wrapline(r(y-a)'' ''++"// ")l" /":z
where
z=w a e
x=r(a+1-y)'' ''++"/"
wrapline b l a=b++i l++a
r=replicate
main=interact$unlines.spider.read