Posicionamento aleatório de itens com aparência determinística?


7

Estou trabalhando em um jogo de rolagem lateral e quero gerar uma floresta para o fundo. Quero que o plano de fundo seja o mesmo para todos, para garantir que a qualidade seja a mesma. Também não tenho acesso a um gerador de números aleatórios semeados, então não consigo encontrar uma boa semente e partir daí.

Ideias?


7
Por que você não tem acesso a um gerador de números aleatórios semeados?

É um programa como um criador de jogos e não possui um :( #

4
Que criador de jogos não oferece um gerador de números aleatórios semeado? Esquisito.

7
Marcá-lo com o mecanismo que você está usando nos ajudaria a ser mais específico nas respostas.
Martin Sojka

Respostas:


15

A maneira mais óbvia provavelmente seria escrever um gerador de números aleatórios. Especialmente porque você não precisa atender a nenhum padrão particularmente alto de aleatoriedade (apenas falta de padrões obviamente visíveis), é muito fácil escrever um bastante razoável em menos de meia dúzia de linhas de código.

Você pode adicionar um argumento que torne a densidade do objeto a mesma para melhorá-la, se necessário


3
Esse algoritmo produz conjuntos de números aleatórios de qualidade muito boa (como no bom "criptográfico" ) (e mesmo usando 0 porque sua semente não o quebra) - foi portado para vários idiomas diferentes (fonte incluída), e é rápido : burtleburtle.net/bob/rand/isaacafa.html
Randolf Richardson

6

Tente isso. Itere dos números 1 para n, onde n é o número de árvores que você deseja desenhar. Calcule um hash em cada número. Use o hash como entrada para a função que desenha ou posiciona os elementos em segundo plano. Por exemplo, você pode usar os primeiros 8 bits de um hash MD5 de 128 bits como a porcentagem x, o próximo como a porcentagem y, o próximo como algum tipo de escala de x, etc. Se você usar a mesma função de hash, e fornecer as mesmas entradas, cada vez que você a executa, obtém a mesma saída.

Isso deve dar absolutamente boa aleatoriedade e será determinístico.

Além disso, se essa não for uma boa resposta, deixe um comentário explicando o porquê.

Olhando a wikipedia, esse método parece promissor:

http://en.wikipedia.org/wiki/Random_number_generation#Computational_methods


Eu não sou o único downvoting apenas tentando descobrir isso ainda :)

Obrigado. Apenas um pouco frustrado quão difícil é ganhar 50 pontos para que eu possa contribuir comentários ...

Isso é bastante alto (calculando uma função de hash segura para cada elemento) para algo que funcionaria bem com um PRNG. (Eu não estou downvoting você, apenas explicando porque eu não acho que é a melhor solução.)

Acordado. Talvez pudesse ser mais eficiente usar um algoritmo de hash rápido, mas ruim, e implementá-lo como um fluxo de bits para não desperdiçar nenhum?

5

Se você tiver acesso a qualquer tipo de hash (como MD5) ou soma de verificação (como CRC32), poderá apenas hash uma sequência de números.

Caso contrário, o PRNG mais simples provavelmente seria o Gerador de Congratulações Lineares . Ele tem um nome complicado, mas escrever um é extremamente simples:

Escolha três constantes, m , a e c .
Comece definindo x anterior à sua semente.
Então, toda vez que você quiser gerar um novo valor x próximo , faça

x próximo = (a * x anterior + c) mod m  
x prev = x próximo

Algumas boas opções para m , a e c podem ser encontradas aqui .


3

Dado que um número aleatório gerado gerado é essencialmente apenas uma tabela de consulta com a semente sendo o deslocamento (índice inicial), você pode configurar um simples lendo um arquivo de números CSV (valores separados por vírgula).

Enquanto todas as instâncias usarem a mesma semente, ela será determinística, mantendo-a pseudo-aleatória.



2

Uma possibilidade é usar um algoritmo chamado ruído simplex , inventado por Ken Perlin (conhecido por Perlin Noise). Uma característica interessante do ruído simplex (como o ruído Perlin) é que ele pode ser lado a lado - ou seja, apenas uma pequena região fora da área potencial precisa ser calculada e isso pode ser repetido em toda a área sem costuras visíveis.

Para que a função de ruído seja repetível, ou seja, sempre produza o mesmo valor para um determinado ponto de entrada, os gradientes precisam ser pseudo-aleatórios, não verdadeiramente aleatórios. Eles precisam ter variação suficiente para ocultar o fato de que a função não é verdadeiramente aleatória, mas muita variação causará comportamento imprevisível para a função de ruído

O ruído simplex pode ser gerado mais rapidamente que o ruído Perlin e não requer um gerador de números aleatórios. Não é arbitrário implementar apenas conhecendo a teoria, mas há algum código fonte para ajudá-lo ( referenciado na Wikipedia ).

Outras opções para gerar ruído pseudo-aleatório são fractais e wavelets .

Na sua situação, você usaria uma dessas técnicas para gerar uma série de dados em uma dimensão e, em seguida, aplicaria um limite para determinar se uma árvore deve ser colocada nessa posição.


1

Resposta mais simples: faça com que seu programa carregue um arquivo com números pré-gerados e escreva um utilitário simples para gerar números aleatórios (ou algorítmicos em qualquer caso) para salvar nesse arquivo.

Dessa maneira, você pode gerar arquivos que são praticamente bons e ajustar manualmente as partes restantes que são ruins, sem entrar no problema em que cada semente aleatória que você tenta tem algum problema.


Eu acho que isso, juntamente com qualquer uma das abordagens dadas como respostas para gerar os números, será a mais fácil de implementar no mecanismo de prateleira que você está usando.
technomalogical 23/09

0

Outra abordagem:

Use uma cifra de bloco para "criptografar" uma série de números de 1 a N, usando uma chave fixa. O TEA é fácil de implementar e bastante rápido.

Uma vantagem dessa abordagem é que, se você não gostar da série de números "aleatórios" que receber, poderá tentar uma chave de criptografia diferente e obter uma série totalmente diferente.

Ao utilizar nosso site, você reconhece que leu e compreendeu nossa Política de Cookies e nossa Política de Privacidade.
Licensed under cc by-sa 3.0 with attribution required.