Disegna una spirale in una scatola


13

spirale

Questa spirale geometrica sembra complicata, ma è abbastanza semplice da disegnare; prendi la seguente scatola:

scatola

Traccia una linea retta tra l'angolo del riquadro e una certa distanza impostata sopra l'angolo successivo in senso antiorario.

1 riga

Continua questo schema verso l'interno, rimanendo sempre a quella distanza dall'angolo della linea successiva. Ecco alcune altre righe in.

linee di muggito

Come puoi vedere, mentre il modello continua, la spirale si avvicina al centro e le caselle che disegni iniziano a ruotare. Si noti che la distanza rimane costante, indipendentemente dall'angolo.

La sfida

The Inspiration (e anche grazie alla persona meravigliosa che mi ha fatto conoscere questo concetto <3)

Dato un input numerico (possibilmente frazionario) da 1 a 25, scrivere un'immagine su disco che utilizza questo modello o visualizzare l'output sullo schermo, dove la distanza da ciascun angolo è la distanza di un lato iniziale del riquadro diviso per l'input . Continuare il motivo verso l'interno fino a quando la distanza dall'angolo specificato non è maggiore della lunghezza del lato successivo.

Regole

  • Non è possibile utilizzare i built-in per questa creazione a spirale, ma è possibile utilizzare i built-in di elaborazione delle immagini.
  • Se si scrive su disco, è necessario generare un'immagine in uno dei formati .jpg, .gif, .tiff, .pbm, .ppm e .png.
  • La lunghezza del lato iniziale deve essere di almeno 500 pixel.
  • L'angolo iniziale può essere qualunque tu scelga.
  • Come sempre, le scappatoie standard non sono ammesse.


Esiste un minimo per quanti livelli deve essere profonda questa spirale?
— LegionMammal978,

@ LegionMammal978 Non chiederei mai un input maggiore di 25, lo aggiungerò.
— Addison Crump

Includere .pbm o .ppm potrebbe aiutare alcuni dei linguaggi meno grafici.
— trichoplax,

Risposte:


12

Scarpe (rubino) 163 byte

Shoes è un toolkit GUI basato su rubini.

Shoes.app{n=ask('').to_f
r=s=5E2
a=[0,s*i="i".to_c,s*i+s,s,0]
(q=a[-3]-a[-4]
r=q.abs/s*n
a<<a[-4]+q/r)while r>1
1.upto(a.size-1){|j|line *(a[j-1].rect+a[j].rect)}}

Ungolfed

Shoes.app{ 
  n=ask('').to_f                 #Open a dialog box with no message, get n from user
  r=s=5E2                        #Initialize s to sidelength=500. r can be initialized to any vale, we use the same one for convenience.
  a=[0,s*i="i".to_c,s*i+s,s,0]   #intialize array a with 5 points needed to draw a square, in complex number format (first point=0 is duplicated.)

  (
    q=a[-3]-a[-4]                #find the vector from point plotted 4 before to the following point (plotted 3 before)
    r=q.abs/s*n                  #r is the scale factor
    a<<a[-4]+q/r                 #add a new point derived from a[-4] by moving toward a[-3] by a distance s/n 
  )while r>1                     #break loop when length of line is less than s/n

  1.upto(a.size-1){|j|           #for all points except 1st and last one
    line *(a[j-1].rect+a[j].rect)#take the two complex numbers correspondimg to the current and previous point,
  }                              #convert to 2-element arrays (rectangular coordinates
}                                #combine to make a 4-element array, use * to splat into 4 parameters, and draw using the line method.

Uscite n = 4 e n = 25

inserisci qui la descrizione dell'immagine

Nota che la forma termina sempre in un triangolo, che collassa ulteriormente in una linea. La sostituzione size-1con sizenon fa alcuna differenza per l'aspetto dell'output e risparmierebbe 2 byte, ma l'ho lasciato per correttezza teorica.

Uscita n = 300

Ispirato da un commento di OP, i numeri più alti sembrano fantastici!

inserisci qui la descrizione dell'immagine


Lo spazio che segue linenella riga inferiore è necessario?
— Addison Crump

@CoolestVeto purtroppo sì. la *converte l'array di quattro elementi formato dalla conversione dei numeri complessi in quattro parametri line. La sintassi standard è line(*(a[j-1].rect+a[j].rect))quindi rimuovere le parentesi e aggiungere uno spazio è già un risparmio di un byte. La rimozione dello spazio fa sì che Ruby provi a moltiplicarsi lineper il contenuto delle parentesi, il che non ha senso e provoca un errore. C'è un po 'di golf da fare qui, ma non quello. Ci penserò più tardi.
— Level River St

Sono quasi certo che puoi sbarazzarti delle parentesi attorno all'argomento upto. Inoltre, hai provato a rimuovere il ('')dopo ask? Non l'ho provato, ma potrebbe non essere necessario
— Finanziate la causa di Monica il

3
L'output per 100 è bellissimo .
— Addison Crump,

1
@CoolestVeto Trovo n = 100 un po 'inquietante; salta fuori e diventa tutto 3D su di me. Ho pubblicato n = 300 che è complessivamente più scuro e quindi più calmo.
— Level River St

3

Java, 1056 1005 985 948 522 508 507 504 502 501 493 492 488 474 465 458 byte

import java.awt.*;interface G{static void main(String[]a){new Frame(){int s=499,o=s,e,i,x,y;{o/=new Float(a[0]);add(new Component(){public void paint(Graphics g){g.drawRect(0,0,s,s);int[]p={s,s,s,0,0,0,0,s};for(double d=s,t;d>o;t=o/d,i=e*2,x=(int)((1-t)*p[i]+t*p[(2+i)%8]+.5),y=(int)((1-t)*p[1+i]+t*p[(3+i)%8]+.5),g.drawLine(p[(6+i)%8],p[(7+i)%8],x,y),p[i]=x,p[1+i]=y,e=++e%4,i=e*2,x=p[(2+i)%8]-p[i],y=p[(3+i)%8]-p[1+i],d=Math.sqrt(x*x+y*y));}});show();}};}}

Grazie a CoolestVeto ed ECS per altri modi per ridurre le dimensioni. :-)


Ok, l'ho minimizzato un po ', ma c'è sicuramente più possibilità, ho codificato troppo orientato agli oggetti per essere minimalista dei personaggi MrGreen
— Vampire

@AlexA. Se in seguito dovessi migliorare il mio codice e renderlo più breve, posso semplicemente aggiornare il post con la versione più breve?
— Vampiro,

@ BjörnKautler Yup, va bene! :) Sto lavorando su alcuni posti per accorciare adesso.
— Addison Crump,

1
@ BjörnKautler Certamente puoi!
— Alex A.

1
Caspita, non ho mai visto più di 500 byte cancellati da una risposta. : O
— Addison Crump,

1

Groovy, 412 411 403 398 byte

import java.awt.*
new Frame(){
def s=499,o=s/(args[0]as float),e=0,i,a,b,d,t
{add new Component(){void paint(Graphics g){g.drawRect 0,0,s,s
p=[s,s,s,0,0,0,0,s]
for(d=s;d>o;d=Math.sqrt(a*a+b*b)){t=o/d
i=e*2
a=(int)((1-t)*p[i]+t*p[(2+i)%8]+0.5)
b=(int)((1-t)*p[1+i]+t*p[(3+i)%8]+0.5)
g.drawLine p[(6+i)%8],p[(7+i)%8],a,b
p[i]=a
p[1+i]=b
e=++e%4
i=e*2
a=p[(2+i)%8]-p[i]
b=p[(3+i)%8]-p[1+i]}}}
show()}}

Ho problemi a farlo funzionare con Groovy 2.4.4: Caught: groovy.lang.MissingMethodException: No signature of method: static s.div() is applicable for argument types: (java.lang.Float) values: [25.0] Possible solutions: is(java.lang.Object), wait(), run(), run(), find(), any() groovy.lang.MissingMethodException: No signature of method: static s.div() is applicable for argument types: (java.lang.Float) values: [25.0] Possible solutions: is(java.lang.Object), wait(), run(), run(), find(), any() at s$1.<init>(s.groovy:3) at s.run(s.groovy:2)
— Dieter,

Con 2.3.9 funziona bene per me.
— Vampiro,
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.