Campo Minado no Trabalho

18

Todo mundo conhece o antigo jogo do caça-minas que acompanha o Windows XP. É uma grade simples com uma matriz 9x9 de células contendo um número (indicando quantas minas estão adjacentes a ela) ou uma mina.

insira a descrição da imagem aqui

O desafio é gerar uma grade 9x9 aleatória com 10 bombas dadas qualquer semente inteira (até o maior int da sua máquina / idioma) com pontos brownie se você implementar o PRNG você mesmo

saída de exemplo: as células contêm números de 0 a 8 ou * para minas

*101*1000
110111000
123210000
1***10000
123210011
00000002*
00000114*
000112*3*
0001*2121

O menor código em bytes vence. Regras padrão etc, etc.

Aaron
fonte
3
Você deve indicar o que os números significam :)
Nathan Merrill
4
O Microsoft Minesweeper é muito mais antigo que o XP e os jogos do tipo dragador de minas datam de pelo menos os anos 60.
AdmBorkBork 02/09
11
Além disso, não tenho tempo para jogar Minesweeper enquanto trabalho - estou muito ocupado com o PPCG. ;-)
AdmBorkBork 02/02
1
O que conta como um PRNG, exatamente? Quantas configurações diferentes ele deve ser capaz de produzir? Podemos não usar a semente e apenas gerar uma configuração diferente de cada vez, se a nossa língua tem um PRNG que é automaticamente initallized a uma semente "aleatório"?
Luis Mendo
1
@ TimmyD Mas a versão do XP é a primeira versão que tinha uma grade 9x9. Qualquer coisa mais antiga usa uma grade 8x8 para iniciantes. #outnerded;)
mbomb007

Respostas:

3

Dyalog APL, 40 bytes

⎕rl←1⋄(1,¨a)⍕¨{⍉3+/0,⍵,0}⍣2⊢a←9 9⍴9≥?⍨81

(assume ⎕io←0)

o 1in ⎕rl←1é a semente

da direita para esquerda:

?⍨81é o mesmo que 81?81- uma permutação aleatória

9≥ resulta em uma máscara de bit contendo dez 1s em posições aleatórias, o restante são 0s

a←9 9⍴ remodelar para um quadrado de 9 por 9 e chamá-lo de "a"

{ }⍣2 faça o seguinte duas vezes:

⍉3+/0,⍵,0 soma da janela deslizante de 3 colunas (assuma 0s fora) e transponha

(1,¨a)⍕¨é o formato (converter em string) cada. O argumento esquerdo para especifica o número total de caracteres e caracteres fracionários no resultado. Se não puder formatar de acordo com essa especificação, gera uma *- uma coincidência de sorte para este problema. aserá 1 onde as minas estão - tentar encaixar uma parte inteira e fracionária em um único caractere é impossível; portanto, essas aparecerão como *s.

ngn
fonte
Você pode explicar a ⎕io←0suposição? Eu não estou familiarizado com Dyalog APL ...
Aaron
1
Os índices de matriz no Dyalog são baseados em 1 por padrão. Configuração ⎕io(o " Índice de Origem ") para 0 torna-base 0 e muda algumas primitivas em conformidade, por exemplo, ⍳3será 0 1 2, não 1 2 3. Isso pode ser feito programaticamente ( ⎕io←0) ou a partir das preferências na GUI. Ter essa escolha é um erro de 50 anos que ainda divide a pequena comunidade de APL de hoje.
NGN
5

MATLAB, 94 93 bytes

rng(input(''));x(9,9)=~1;x(randperm(81,10))=1;y=[conv2(+x,ones(3),'s')+48 ''];y(x)=42;disp(y)

Exemplo de execução (a primeira linha após o código é a entrada digitada pelo usuário):

>> rng(input(''));x(9,9)=~1;x(randperm(81,10))=1;y=[conv2(+x,ones(3),'s')+48 ''];y(x)=42;disp(y)
99
*10001*2*
220001232
*201111*1
*312*1111
12*211000
011211000
0001*1000
000112110
000001*10

Explicação

rng(input(''));

pega um número inteiro e o usa como semente. (Isso funciona nas versões modernas do MATLAB. As versões antigas podem precisar de uma sintaxe diferente.)

x(9,9)=~1;

atribui lógico 0, ou false(obtido negando logicamente 1) à entrada (9,9)de uma matriz x. O restante das entradas também é inicializado automaticamente para lógico 0.

x(randperm(81,10))=1; 

atribui 1(convertido automaticamente para lógico 1ou true) para 10as 81entradas de x, escolhidas aleatoriamente sem substituição. Essas entradas são as que contêm bombas.

conv2(+x,ones(3),'s')

é uma abreviação de conv2(+x,ones(3),'same'). Ele envolve a matriz x(que precisa ser convertida em double, usando +) com uma vizinhança 3 × 3 1. Isso conta quantas bombas estão adjacentes a cada entrada. Para entradas que contêm uma bomba, ela inclui essa bomba, mas o valor será substituído posteriormente.

y=[...+48 ''];

adiciona 48 ao valor, para converter de número em código ASCII. Concatenar com a matriz vazia lança esses códigos ASCII em caracteres.

y(x)=42;

atribui 42 (código ASCII para '*') às posições das bombas. Essas posições são dadas por x, que é usada aqui como um índice lógico.

disp(y)

exibe o resultado.

Luis Mendo
fonte
4

Javascript (ES6), 204 ou 198 bytes

PRNG personalizado (204 bytes)

s=>(p=-1,S=n=>(x=p%9-(n+=p)%9)*x-64&&b[n]=='*',T=n=>S(n)+S(-n),b=[...'*00000000'.repeat(9)]).sort(_=>(s=(22695477*s+1)>>>0)&1||-1).map(c=>(p++,c=='0'?T(1)+T(8)+T(9)+T(10):c)).join``.match(/.{9}/g).join`
`

Este código está usando um gerador congruencial linear com multiplicador 22695477e incremento 1(esta é a implementação do Borland C / C ++).

Devido à baixa eficiência do PRNG durante a fase de aquecimento, tive que colocar uma bomba por linha (em vez de 10 no início ou 10 no final da matriz não embaralhada). Portanto, existem apenas 9 bombas. Eu posso tentar consertar isso mais tarde.

Além disso, deve haver uma maneira mais simples / mais curta de processar a verificação 'fora do quadro', (x=p%9-(n+=p)%9)*x-64mas não consigo descobrir agora.

Usando Math.random () (198 bytes)

s=>(p=-1,S=n=>(x=p%9-(n+=p)%9)*x-64&&b[n]=='*',T=n=>S(n)+S(-n),b=[...'**********'+'0'.repeat(71)]).sort(_=>Math.random()-.5).map(c=>(p++,c=='0'?T(1)+T(8)+T(9)+T(10):c)).join``.match(/.{9}/g).join`
`

Este inclui 10 minas, conforme solicitado.

Demo

let f =
_=>(p=-1,S=n=>(x=p%9-(n+=p)%9)*x-64&&b[n]=='*',T=n=>S(n)+S(-n),b=[...'**********'+'0'.repeat(71)]).sort(_=>Math.random()-.5).map(c=>(p++,c=='0'?T(1)+T(8)+T(9)+T(10):c)).join``.match(/.{9}/g).join`
`
console.log(f())

Arnauld
fonte
'**********'+'0'é igual a '**********'+0; que salva dois bytes na versão de 198 bytes.
Paul Schmitz
@PaulSchmitz - Infelizmente, isso '0'deve ser repetido e 0.repeat()não funcionaria.
Arnauld
Opa, eu pensei que seria executado como ...('**********'+0).repeat(71). Desculpe.
Paul Schmitz
3

Python 2, 269 266 264 bytes

from random import*
seed(input())
z=1,0,-1
n=range(9)
m=[[0]*9 for _ in n]
for x,y in sample([[x,y]for x in n for y in n],10):
 m[x][y]=-9
 for a in z:
  for b in z:
    if 0<=x+a<9>0<=y+b<9:m[x+a][y+b]+=1 # it gets displayed as 4 spaces, but the beginning of this line is a single tab
print("\n".join("".join([`c`,'*'][c<0]for c in l)for l in m))

Experimente em ideone.com

Economizou 2 bytes graças a Aaron.

Muito provavelmente ainda jogável.

Explicação

randomé importado para usar seedpara propagar o PRNG e sampleselecionar dez locais de bomba aleatoriamente. mé uma matriz 9 x 9, salvando a placa. Para cada local da bomba, a entrada correspondente mé definida como -9e todas as entradas vizinhas são incrementadas. Dessa forma, macaba contendo a contagem de bombas adjacentes para células que não são de bomba e um número negativo para células de bomba. Os finais printgravuras toda a placa fazendo a iteração através de todas as linhas lem me todas as células cem l.

LevitatingLion
fonte
Para que exatamente é usado 'aleatório', exatamente?
clismique 2/09/16
@ Qwerp-Derp provavelmente para semear o gerador de números aleatórios indiretamente usado porsample()
Patrick Roberts
salvar 2 bytes por mistura de travessões de guia no interior for a in z:do bloco (somente pitão 2.x)
Aaron
3

R, 187 bytes

set.seed();x=1:121;y=x[!(x%%11 %in% 0:1|(x-1)%/%11 %in% c(0,10))];z=sample(y,10);x=x*0;for(t in z){p=t+c(-10:-12,-1,1,10:12);x[p]=x[p]+1};x[z]=9;m=data.frame(matrix(x[y],9));m[m==9]='*';m

Experimente no Ideone

Explicação:

set.seed() pegue uma semente cst.

x é o índice para uma matriz 11 * 11

y é o índice da matriz 9 * 9 na matriz 11 * 11

z é o índice da bomba

x=x*0 inicializar o valor da matriz

O loop adiciona 1 a x em caso de bomba adjacente.

YCR
fonte
1
Eu acho que você precisa usar o argumento set.seed () como entrada.
BLT
2

JavaScript ES6, 244 bytes

f=(a=[...Array(11)].map(_=>Array(11).fill(0)),n=10,r=_=>Math.random()*9|0,x=r(),y=r())=>a[x+1][y+1]>8||[0,1,2].map(i=>[0,1,2].map(j=>a[x+i][y+j]++),a[x+1][y+1]=9)&&--n?f(a,n):a.slice(1,-1).map(a=>a.slice(1,-1).map(n=>n<9?n:`*`).join``).join`
`
;o.textContent=f()
<pre id=o>

Neil
fonte
Você pode especificar qual parte é o seu código.
NoOneIsHere 2/16
@NoOneIsHere Os primeiros 244 bytes, espero ;-) A primeira linha deve ter 242 bytes, então há a nova linha e o `caractere.
Neil
1

Ruby , 181 194 183 + 1 = 184 bytes

Esqueci de realmente colocar a semente, gritos. Usa a -nbandeira.

Experimente online!

srand$_.to_i
a=[0]*81
[*0..80].sample(10).map{|i|w=i%9;h=i/9;a[i]=-99
(r=-1..1).map{|x|x+=w
x<0||x>8?0:r.map{|y|y+=h
y<0||y>8?0:a[9*y+x]+=1}}}
puts a.map{|c|c<0??*:c}.join.scan /.{9}/
Value Ink
fonte
0

Python 2 , 172 bytes

from random import*
seed(input())
r=range
b=set(sample(r(81),10))
for j in r(9):print''.join([[`len({x-10,x-9,x-8,x-1,x+1,x+8,x+9,x+10}&b)`,'*'][x in b]for x in r(j,81,9)])

Experimente online!

tsh
fonte