Uccidilo col fuoco


30

Dichiarazione di non responsabilità: la storia raccontata all'interno di questa domanda è del tutto inventata e inventata esclusivamente allo scopo di fornire un'introduzione.

Sono un malvagio agricoltore e per aumentare il prezzo del grano nella mia zona, ho deciso di bruciare i campi di tutti i contadini intorno a me. Mi piacerebbe davvero vedere i campi andare in fiamme (così posso usare la mia risata malvagia e strofinarmi le mani insieme alla gioia), ma anche io non voglio essere sorpreso a guardare, quindi ho bisogno che tu simuli il campo incenerito per me.

Il tuo compito:

Scrivi un programma o una funzione che accetta come input un campo e restituisce le fasi di masterizzazione fino a quando l'intero campo non è cenere. Una sezione specifica del campo che è in fiamme è rappresentata da un numero intero che rappresenta l'intensità della fiamma. Un incendio inizia da "1" e passa a "2", quindi a "3" e così via. Una volta che un incendio raggiunge "4", cattura qualsiasi area adiacente direttamente (non in diagonale) infiammabile al fuoco. Quando raggiunge "8", si esaurisce alla successiva iterazione e si trasforma in cenere, rappresentata da una "A". Quando un'area non è stata ancora toccata dal fuoco, è rappresentata da uno "0". Ad esempio, se il campo è simile al seguente:

100
000

Il tuo programma dovrebbe produrre questo:

100
000

200
000

300
000

410
100

520
200

630
300

741
410

852
520

A63
630

A74
741

A85
852

AA6
A63

AA7
A74

AA8
A85

AAA
AA6

AAA
AA7

AAA
AA8

AAA
AAA

Se lo desideri, puoi sostituire i simboli sopra con qualsiasi set di simboli che scegli, a condizione che siano coerenti e distinti tra loro.

Ingresso:

La posizione iniziale del campo, in qualsiasi forma standard, come una stringa delimitata da nuova riga come sopra.

Produzione:

Il campo in ogni iterazione mentre brucia, sia come una matrice, sia come una stringa delimitata da un carattere.

Casi test:

0301
000A
555
 |
 v
0301
000A
555

1412
010A
666

2523
020A
777

3634
030A
888

4745
141A
AAA

5856
252A
AAA

6A67
363A
AAA

7A78
474A
AAA

8A8A
585A
AAA

AAAA
6A6A
AAA

AAAA
7A7A
AAA

AAAA
8A8A
AAA

AAAA
AAAA
AAA

punteggio:

Questo è , il punteggio più basso in byte vince!


1
Quanto può variare la forma? Le parti non rettangolari sono sempre "fori" sul bordo destro o possono esserci spazi nel campo?
PurkkaKoodari,

3
Quindi qualcosa che colpisce 4 fa scoppiare un fuoco nei quadrati adiacenti, ma qualcosa che inizia a 4 o più alto no? Non è molto realistico.
laszlok,

14
"Disclaimer: la storia raccontata all'interno di questa domanda è del tutto inventata e inventata esclusivamente allo scopo di fornire un'introduzione." -> Inizia con "Sono un contadino malvagio [che vuole fare cose malvagie]". Molto intelligente. Nessuno ti collegherà i campi in fiamme ora .
J_F_B_M,

3
È possibile per la cenere iniziale separare il campo in due, in modo che una parte di esso non bruci mai?
aschepler,

9
Se il fuoco che non si diffonde al di sopra di 4 è troppo sconvolgente, immagina che 1-4 sia l'intensità che sta guadagnando il fuoco e che 5-A lo rappresenti in fiamme.
Jeremy Weirich,

Risposte:


1

APL (Dyalog) , 52 byte *

Presuppone ⎕IO←0che è predefinito su molti sistemi. Entra in campo usando 0 per gli slot vuoti, 1 per il campo non ardente, 2 per il nuovo fuoco, 5 per diffondere il fuoco e 10 per la cenere. L'input deve essere almeno 3 × 3, il che non è un problema poiché righe e colonne aggiuntive possono essere riempite di zeri (spazi nel formato OP).

{}{1=c4r←,⍵:1+4r/⍨9⍴⍳210cc}⌺3 3⍣{⍺≡⎕←⍵}

Provalo online!

Il mio formato rende difficile verificare la correttezza, quindi qui una versione con pre e post-elaborazione aggiunte da tradurre da e verso il formato OP.

⍣{... } ripeti fino a:

 la prossima generazione

 è identico a

⎕←⍵ l'attuale generazione, emessa

{... }⌺3 3 sostituisci ogni cella con il risultato di questa funzione applicata al suo vicinato Moore:

 ,⍵ ravel (appiattire) l'argomento; fornisce un elenco di nove elementi

r← assegnare a r

4⊃ scegli il quarto elemento; il centro, ovvero il valore della cella originale

c← assegnare a c

1= è uguale a quello?

: in tal caso, quindi:

  ⍳2 prima ɩ ntegers; 0 1

  9⍴r eshape alla lunghezza nove; 0 1 0 1 0 1 0 1 0

  r/⍨ usalo per filtrare r (questo ottiene solo i vicini ortogonali)

  4∊ ne fa parte quattro? (cioè ci saranno cinque nella prossima generazione?)

  1+ Aggiungi uno; 1 se non ha preso fuoco o 2 se ha preso fuoco

 altro (ovvero il valore corrente è 0 o ≥ 2)

  ×c il signum di c

  c+c plus che (cioè aumento di uno se il fuoco)

  10⌊ minimo dieci e quello (poiché la cenere non si accende)


* In Dyalog Classic, usando ⎕U233A invece di .


Piccolo, ma non si occupa delle modifiche alla scheda. Bloccato a un 3x3.
Suamere,

@Suamere Cosa? La tavola non cambia dimensione, vero?
Adám,

Scusa, non ero chiaro. La tua risposta è fantastica, ma sono consapevole che la soluzione dovrebbe consentire una scheda di dimensioni variabili che può o meno avere lacune "a destra". Gli spazi vuoti nel mezzo non devono essere gestiti. "A destra" sembra significare che una scheda di dimensioni 15 verrebbe costruita come 4x4, tranne che manca il pezzo in fondo a destra. E una scheda di dimensioni 8 verrebbe costruita come una 3x3, tranne per il fatto che manca il pezzo più in basso a destra, ecc. Ecco come ho letto i requisiti della sfida. La tua risposta è attualmente la più breve, ma funziona solo con un 3x3.
Suamere,

@Suamere OP afferma chiaramente che l'input è 2D. Prendo l'input come matrice numerica e consento slot "vuoti" ovunque, sotto forma di zeri. Mentre richiedo che l'input sia almeno 3 × 3 ( OP ha permesso questo ) accetto input di qualsiasi dimensione maggiore. In effetti, se fai clic sul link qui , vedrai che il mio secondo caso di esempio è 2 × 3 con la cella in basso a destra vuota.
Adám,

Gotcha. Non so perché, ma il link Provalo qui ha dei problemi (probabilmente colpa mia), sebbene il tuo nuovo link formattato funzioni bene. Ad esempio: fire '0A000\n0A0A0\n0A0A0\n000A1'funziona perfettamente su quello formattato, ma non riesco a ottenere un equivalente per lavorare con il primo collegamento. Probabilmente sto facendo qualcosa di sbagliato. Questo non funziona per me:f ↑(0 0 0)(0 1 0)(0 0 0)
Suamere,

15

Python 3 , 232 byte

def f(j):
 k=[[int(min(9,j[x][y]+(j[x][y]>0)or 3in(lambda k,x,y:[k[i][j]for i,j in[[x-1,y],[x+1,y],[x,y-1],[x,y+1]]if(-1<i<len(k))and(-1<j<len(k[i]))])(j,x,y)))for y in range(len(j[x]))]for x in range(len(j))]
 if k!=j:print(k);f(k)

Provalo online!

-3 byte grazie a officialaimm unendo l'altro lambda in f(sembra disordinato ma salva byte e questo è tutto ciò che ci interessa)
-8 byte grazie a Mr. Xoder
-26 byte grazie a ovs
-6 byte grazie a ppperry


Come faccio ad aggiungere uno spazio vuoto, come quello nell'esempio?
Tuskiomi,

10

JavaScript (ES6), 217 210 207 204 193 192 190 byte

Salvato 2 byte grazie al suggerimento di @ Shaggy di usare 9as A.

f=F=>[F,...(t=[],y=0,g=x=>(r=F[y])?(x||(t[y]=[]),r[x]+1)?(t[y][x]=r[x]<8?r[x]+(r[x]>0|[r[x-1],r[x+1],F[y-1]&&F[y-1][x],F[y+1]&&F[y+1][x]].includes(3)):9,g(x+1)):g(0,y++):t)(0)+""!=F?f(t):[]]

// test code
test=s=>{
  var test = document.querySelector("#in").value.split`\n`.map(e => Array.from(e).map(e => parseInt(e)));
  var out = f(test);
  document.querySelector("#out").innerHTML = out.map(e => e.map(e => e.join``).join`\n`).join`\n\n`;
};window.addEventListener("load",test);
<textarea id="in" oninput="test()">0301&#10;0009&#10;555</textarea><pre id="out"></pre>

Utilizza 9invece di A. Input come una matrice 2D di numeri interi. Output come una matrice di tali array.


Potresti salvare qualcosa usando 9invece di A?
Shaggy

7

Simulazione del mondo (in Emoji) , 1407 byte?

Non ti piace usare una spiegazione esplorabile come linguaggio di programmazione? L'aspetto negativo di questo è che di solito non esiste un programma molto ben definito, quindi in questo caso sto usando il JSON che esporta. (se hai idee migliori, fammi sapere)

{"meta":{"description":"","draw":1,"fps":1,"play":true},"states":[{"id":0,"icon":"0","name":"","actions":[{"sign":">=","num":1,"stateID":"4","actions":[{"stateID":"1","type":"go_to_state"}],"type":"if_neighbor"}],"description":""},{"id":1,"icon":"1","name":"","description":"","actions":[{"stateID":"2","type":"go_to_state"}]},{"id":2,"icon":"2","name":"","description":"","actions":[{"stateID":"3","type":"go_to_state"}]},{"id":3,"icon":"3","name":"","description":"","actions":[{"stateID":"4","type":"go_to_state"}]},{"id":4,"icon":"4","name":"","description":"","actions":[{"stateID":"5","type":"go_to_state"}]},{"id":5,"icon":"5","name":"","description":"","actions":[{"stateID":"6","type":"go_to_state"}]},{"id":6,"icon":"6","name":"","description":"","actions":[{"stateID":"7","type":"go_to_state"}]},{"id":7,"icon":"7","name":"","description":"","actions":[{"stateID":"8","type":"go_to_state"}]},{"id":8,"icon":"8","name":"","description":"","actions":[{"stateID":"9","type":"go_to_state"}]},{"id":9,"icon":"A","name":"","description":"","actions":[]}],"world":{"update":"simultaneous","neighborhood":"neumann","proportions":[{"stateID":0,"parts":100},{"stateID":1,"parts":0},{"stateID":2,"parts":0},{"stateID":3,"parts":0},{"stateID":4,"parts":0},{"stateID":5,"parts":0},{"stateID":6,"parts":0},{"stateID":7,"parts":0},{"stateID":8,"parts":0},{"stateID":9,"parts":0}],"size":{"width":9,"height":9}}}

Provalo qui o qui:

<iframe width="100%" height="450" src="http://ncase.me/simulating/model/?remote=-Kr2X939XcFwKAunEaMK" frameborder="0"></iframe>


6

Retina , 103 96 88 byte

^
¶
;{:`

T`0d`d
(?<=¶(.)*)0(?=4|.*¶(?<-1>.)*(?(1)_)4|(?<=40|¶(?(1)_)(?<-1>.)*4.*¶.*))
1

Provalo online! Usi 9per la cenere; questo può essere modificato al costo di 4 byte usando T`1-8`2-8A. Modifica: salvato 6 byte grazie a @MartinEnder. Spiegazione:

^
¶

Aggiungi un separatore in modo che le uscite non si incontrino. (Aiuta anche quando si abbina di seguito.)

;{:`

Non stampare lo stato finale (che è lo stesso dello stato precedente che è già stato stampato). Ripetere fino a quando il passaggio non cambia lo stato. Stampa lo stato corrente prima di ogni passaggio.

T`0d`d

Fai avanzare l'intensità di tutto il fuoco.

(?<=¶(.)*)0(?=4|.*¶(?<-1>.)*(?(1)_)4|(?<=40|¶(?(1)_)(?<-1>.)*4.*¶.*))
1

Accendi i campi non illuminati come appropriato. Sotto-spiegazione:

(?<=¶(.)*)

Misura il numero di colonna di questo campo spento.

0

Abbina il campo non illuminato.

(?=4

Cerca un campo adatto a destra.

  |.*¶(?<-1>.)*(?(1)_)4

Cerca un campo adatto nella stessa colonna (usando un gruppo di bilanciamento) nella riga in basso. Si noti che se l'ingresso potrebbe essere garantito rettangolare, questo potrebbe essere semplificato |.*¶(?>(?<-1>.)*)4per un risparmio di 3 byte.

  |(?<=40

Cerca un campo adatto a sinistra. (Dal momento che guardiamo dal lato destro del campo, vediamo anche il campo non illuminato.)

      |¶(?(1)_)(?<-1>.)*4.*¶.*))

Cerca un campo adatto nella stessa colonna nella riga sopra. Poiché si tratta di un lookbehind e quindi di una corrispondenza da destra a sinistra, la condizione del gruppo di bilanciamento deve apparire prima delle colonne che sono state abbinate dal gruppo di bilanciamento.


5

Perl 5 , 365 byte

@a=map{[/./g]}<>;do{say@$_ for@a;say;my@n=();for$r(0..$#a){$l=$#{$a[$r]};for(0..$l){$t=$a[$r][$_];$n[$r][$_]=($q=$n[$r][$_])>$t?$q:$t==9?9:$t?++$t:0;if($t==4){$n[$r-1][$_]||=1if$r&&$_<$#{$a[$r-1]};$n[$r+1][$_]||=1if$r<$#a&&$_<$#{$a[$r+1]};$n[$r][$_-1]||=1if$_;$n[$r][$_+1]||=1if$_<$l}}}$d=0;for$r(0..$#a){$d||=$a[$r][$_]!=$n[$r++][$_]for 0..$#{$a[$r]}}@a=@n}while$d

Provalo online!

Usa '9' invece di 'A' per indicare una posizione bruciata.

spiegato

@a=map{[/./g]}<>;   # split input into a 2-D array

do{
say@$_ for@a;say;   # output the current state
my@n=();            # holds the next iteration as it's created
for$r(0..$#a){      # loop through rows
  $l=$#{$a[$r]};    # holder for the length of this row
  for(0..$l){
    $t=$a[$r][$_];  # temporary holder for current value
    $n[$r][$_]=($q=$n[$r][$_])>$t?$q:$t==9?9:$t?++$t:0; #update next iteration
    if($t==4){      # ignite the surrounding area if appropriate
      $n[$r-1][$_]||=1if$r&&$_<$#{$a[$r-1]};
      $n[$r+1][$_]||=1if$r<$#a&&$_<$#{$a[$r+1]};
      $n[$r][$_-1]||=1if$_;
      $n[$r][$_+1]||=1if$_<$l
    }
  }
}
$d=0;              # determine if this generation is different than the previous
for$r(0..$#a){$d||=$a[$r][$_]!=$n[$r++][$_]for 0..$#{$a[$r]}}
@a=@n              # replace master with new generation
}while$d

4

Haskell , 162 byte

import Data.List
i x|x<'9'=succ x|1<2=x
f('3':'@':r)="30"++f r
f(x:r)=x:f r
f e=e
a%b=a.b.a.b
g=map(i<$>).(transpose%map(reverse%f))
h x|y<-g x,y/=x=x:h y|1<3=[x]

Provalo online! Utilizzo: haccetta un campo come un elenco di righe e restituisce un elenco di campi. Un campo non bruciato è indicato da @e cenere da 9, i diversi incendi sono le cifre 1a 8.

  • fgestisce la diffusione del fuoco da sinistra a destra sostituendo tutti i @campi incombusti che hanno ragione su un 3campo in fiamme 0.
  • iincrementa ogni cifra purché sia ​​inferiore a 9.
  • gsi applica fa ciascuna riga, quindi inverte la riga, si applica fnuovamente e torna indietro. Quindi l'elenco delle righe viene trasposto e di nuovo su ogni riga e fviene applicato il suo contrario .
  • hsi applica gall'input fino a quando non cambia più e raccoglie i risultati.

Errore sull'input "" @ 3 @ 1 \ n @@@ 9 \ n555 @@@@@@@@@@@@@ ", poiché per qualche motivo la linea lunga di @s passa a la linea superiore dopo la prima iterazione. Correzione sarebbe fantastico, grazie!
Gryphon - Ripristina Monica

@Gryphon Lo spostamento è causato dalla trasposizione della matrice di caratteri. Funziona se le altre linee sono portate alla stessa lunghezza con un carattere che non rappresenta né un campo, fuoco o cenere, ad es _. Se questo non è accettabile, temo che dovrei eliminare la risposta, perché è incentrata sull'uso di transposee non vedo un modo per risolverlo facilmente senza introdurre tonnellate di byte.
Laikoni,

4

C (gcc) , 308 305 299 297 295 291 byte

#define F B[i][v]
m(A,B,k,y,m,U,i,v)char**B;{do{for(i=k=y=0;i<A;puts(""),++i)for(v=0;v<(m=strlen(B[i]));F=(U=F)>48&&F<56?F+1:F>55?65:(i+1<A&&B[i+1][v]==51||v+1<m&&B[i][v+1]==51||v-1>-1&&B[i][v-1]==52||i-1>-1&&B[i-1][v]==52)&&U<49?49:F,putchar(U),k+=U<49||U>64,++y,++v);puts("");}while(k-y);}

Questo programma definisce una funzione che accetta due input, un puntatore a una matrice di stringhe preceduta dalla sua lunghezza, come consentito da questo I / O predefinito. Emette su STDOUT con una nuova riga finale.

Provalo online!


Funziona per sempre con l'input 80.
aschepler

@aschepler Siamo spiacenti! Ho supposto che tutti i personaggi dovevano trasformarsi in As, ma a quanto pare ho ritenuto sbagliato. Comunque, grazie per l'informazione. Ora è riparato.
R. Kap


@GiacomoGarabello Non riesco a credere di aver dimenticato quella tattica. Grazie per avermi ricordato! :)
R. Kap

4

Ottava, 72 69 byte

a=input(''),do++a(a&a<9);a+=imdilate(a==4,~(z=-1:1)|~z')&~a,until a>8

L'input viene preso come una matrice 2D di numeri e i punti vuoti contrassegnati con Inf. 'A'è stato sostituito con 9. Risultati intermedi (come matrice di numeri) implicitamente stampati.

Provalo online!

Spiegazione:

In un ciclo la funzione imdilate(dilatazione dell'immagine morfologica) dal pacchetto di immagini viene utilizzata per simulare la propagazione del fuoco.


1
Funziona con schede di tutte le dimensioni e anche con un sacco di fori. EG: [0 Inf 0 0 0;0 Inf 0 Inf 0;0 Inf 0 Inf 0;0 0 0 Inf 1]- Molto bello
Suamere,

1

Python 2 , 325 byte

def f(x):
 while{i for m in x for i in m}>{9,''}:
    yield x;i=0
    for l in x:
     j=0
     for c in l:
        if 0<c<9:x[i][j]+=1
        j+=1
     i+=1
    i=0
    for l in x:
     j=0
     for c in l:
        if c==0 and{1}&{x[k[1]][k[2]]==4for k in[y for y in[[i,i-1,j],[i<len(x)-1,i+1,j],[j,i,j-1],[j<len(l)-1,i,j+1]]if y[0]]}:x[i][j]+=1
        j+=1
     i+=1
 yield x

faccetta l'input come una matrice 2D di numeri interi e spazi vuoti contrassegnati con ''. 'A'è stato sostituito con 9. La funzione genera nel tempo un generatore di tutti i campi nello stesso formato.

Provalo online!


1

Ottava , 212 byte

function r(f)b=48;f-=b;c=-16;l=f~=-c;d=17;p=@(x)disp(char(x+b));g=@()disp(' ');p(f);g();while~all(any(f(:)==[0 d c],2))m=f>0&l;f(m)+=1;k=conv2(f==4,[0 1 0;1 0 1;0 1 0],'same')&~m&l;f(k)+=1;f(f>8&l)=d;p(f);g();end

Per eseguire, specificare una matrice di caratteri come:

f = ['0301','000A','555 '];

... Quindi fa:

r(f)

Spiegazione del codice da seguire ...

Provalo online!

Nota: ho provato a eseguire questo codice con tio.run , ma non ho ricevuto alcun output. Ho dovuto usare un altro servizio.


Davvero proprio nel momento in cui voglio pubblicare una risposta di ottava, rispondi prima di me ..
Michthan,

1

PHP, 226 212 210 209 185 177 byte

for($f=file(m);$f!=$g;print"
")for($g=$f,$y=0;$r=$f[$y++];)for($x=-1;~$c=$r[++$x];$f[$y-1][$x]=$c=="0"?strstr($g[$y-2][$x].$r[$x-1].$f[$y][$x].$r[$x+1],51)/3:min(++$c,9))echo$c;

accetta l'input con una nuova riga finale da un file denominato m;9per le ceneri.

Corri con -nro provalo online .


primo approccio: PHP 7.0, 209 byte

for($f=$g=file(m);trim(join($f),"A
");print"
".join($f=$g))for($y=-1;(a&$c=$r[++$x])||$r=$f[$y-=$x=-1];)for(+$c&&$g[$y][$x]=++$c<9?$c:A,$a=4;$a--;$q=$p)$c-4|($w=&$g[$y+$p=[1,0,-1][$a]])[$q+=$x]!="0"||$w[$q]=1;

accetta l'input con una nuova riga finale da un file denominato m .

Corri con -nro provalo online .

Note sulla versione di PHP (per vecchio approccio)

  • per PHP più vecchio di 7.0, sostituire tutto dopo $c-4|con$g[$y+$p=[1,0,-1][$a]][$q+=$x]!="0"||$g[$y+$p][$q]=1;
  • per PHP più vecchio di 5.5, sostituire [1,0,-1][$a]con$a%2*~-($a&2)
  • per PHP più recente di 7.0, sostituire a&$ccon ""<$c, +$ccon 0<$ce $c-4con$c!=4

non funziona per altri casi di test ... sandbox.onlinephpfunctions.com/code/…
g19fanatic

@ g19fanatic fixed & golfed. grazie per averlo notato.
Tito,

0

Ottava, 419 312 byte

M=input('') %take a matrix M as input
[a, b]=size(M); %size M for later
while mean(mean(M))!=9 %while the whole matrix M isn't ashes
M=M+round(M.^0.001); %if there is a nonzero int add 1 to it
for i=1:a %loop over all values of M
for j=1:b
if(M(i,j)==4) %if a value of 4 is found, ignite the zeros around it
if(M(max(i-1,1),j)==0) M(i-1,j)++;end
if(M(min(i+1,a),j)==0) M(i+1,j)++;end
if(M(i,max(j-1,1))==0) M(i,j-1)++;end      
if(M(i,min(j+1,b))==0) M(i,j+1)++;end
elseif(M(i,j)==10) M(i,j)--;
end
end
end
M %display the matrix
end

Provalo online!

Questa è la mia versione che funziona, quindi ora ho ancora bisogno di giocare a golf. Penso che può essere molto più breve se trovo un modo per trovare gli indici del 4 in una matrice, ma non so come.
PS: A è un 9 nel mio codice.


2
Invece di endif endfore endwhilepuoi scrivereend
rahnema1

0

Stencil ( -mode) , 22 byte

S8:'A'0::S⋄(3N)⌈S+s

Provalo online!

Proprio come nell'input di test, usa numeri interi separati da spazi per 0- 8, ' 'per blank e 'A'per A. Ricorda di aggiungere anche spazi vuoti finali.

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.