Question

J'écris un programme de jeu de la vie en mathématique, mais il y a une mise en garde en ce sens que je dois pouvoir appliquer les règles de reproduction à un certain pourcentage des cellules, je veux essayer une nouvelle méthode utilisant MapAt mais liveNeighbors ne le fait pasne fonctionne pas par élément, et je ne peux pas penser à un moyen de le réparer sans faire exactement ce que j'ai fait avant (beaucoup d'indexation désordonnée), est-ce que quelqu'un a des suggestions?(Je suppose que ce sera plus efficace que l'ancienne méthode, qui est répertoriée ci-dessous, sinon faites-le moi savoir, je ne suis qu'un débutant!).

Ce que j'essaie de faire:

 Map[ArrayPlot,FixedPointList[MapAt[update[#,liveNeighbors[#]]&,#,coords]&,Board, 1]]

Ce que j'ai déjà fait:

LifeGame[ n_Integer?Positive, steps_] := Module [{Board, liveNeighbors, update},
  Board = Table [Random [Integer], {n}, {n}];
  liveNeighbors[ mat_] := 
   Apply[Plus,Map[RotateRight[mat,#]&,{{-1,-1},{-1, 0},{-1,1}, {0, -1}, {0, 1}, {1, -1}, {1, 0}, {1, 1}}]];
  update[1, 2] := 1;
  update[_, 3] := 1;
  update[ _, _] := 0;
  SetAttributes[update, Listable];
 Seed = RandomVariate[ProbabilityDistribution[0.7 UnitStep[x] + 0.3 UnitStep[x - 1], {x, 0, 1, 1}], {n, n}];
 FixedPointList[Table[If[Seed[[i, j]] == 1,update[#[[i, j]], liveNeighbors[#][[i, j]]],#[[i, j]]], {i, n}, {j, n}]&, Board, steps]]]

Merci!

Était-ce utile?

La solution

In[156]:= 
LifeGame2[n_Integer?Positive, steps_] := 
 Module[{Board, liveNeighbors, update},
  Board = RandomInteger[1, {n, n}];
  liveNeighbors[mat_] := 
   ListConvolve[{{1, 1, 1}, {1, 0, 1}, {1, 1, 1}}, 
    ArrayPad[mat, 1, "Periodic"]];
  SetAttributes[update, Listable];
  Seed = RandomVariate[BernoulliDistribution[0.3], {n, n}];
  update[0, el_, nei_] := el;
  update[1, 1, 2] := 1;
  update[1, _, 3] := 1;
  update[1, _, _] := 0;
  FixedPointList[MapThread[update, {Seed, #, liveNeighbors[#]}, 2] &, 
   Board, steps]
  ]

Cette implémentation fait la même chose que la vôtre, sauf qu'elle est beaucoup plus rapide:

In[162]:= AbsoluteTiming[
 res1 = BlockRandom[SeedRandom[11]; LifeGame[20, 100]];]

Out[162]= {6.3476347, Null}

In[163]:= Timing[BlockRandom[Seed[11]; LifeGame2[20, 100]] == res1]

Out[163]= {0.047, True}

Autres conseils

En supposant que vous n'ayez pas à rouler votre propre code pour un problème de devoirs, avez-vous envisagé d'utiliser simplement le CellularAutomaton ?

Directement de la documentation, la règle 2D CA:

GameOfLife = {224, {2, {{2, 2, 2}, {2, 1, 2}, {2, 2, 2}}}, {1, 1}};

Et parcourez une grille de 100 x 100 pendant 100 étapes:

ArrayPlot[CellularAutomaton[GameOfLife, RandomInteger[1, {100, 100}], {{{100}}}]]

sortie de CellularAutomaton

Cela vous donnerait au moins une base de référence pour une comparaison de vitesse.

Au lieu de MapAt, vous pouvez utiliser Part avec la syntaxe Span pour remplacer un sous-tableau entier à la fois:

a = ConstantArray[0, {5, 5}];
a[[2 ;; 4, 2 ;; 4]] = {{1, 2, 3}, {4, 5, 6}, {7, 8, 9}}

a dans MatrixForm

HTH!

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top