eca.odin 1.2 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667
  1. package eca
  2. import "core:fmt"
  3. import "core:math/rand"
  4. import "core:time"
  5. import "intrinsics"
  6. elementary_cellular_automata :: proc(state: $T, rule: u8, generations: int, pause: time.Duration = 0)
  7. where intrinsics.type_is_integer(T),
  8. intrinsics.type_is_unsigned(T) {
  9. N :: 8*size_of(state);
  10. output :: proc(state: T) {
  11. buf: [N]byte;
  12. for i in 0..<T(N) {
  13. c := byte('#');
  14. // c := byte(rand.int_max(26) + 'A' + ('a'-'A')*rand.int_max(2));
  15. buf[N-1-i] = state & (1<<i) != 0 ? c : ' ';
  16. }
  17. fmt.println(string(buf[:]));
  18. }
  19. bit :: proc(x, i: T) -> T {
  20. return (x >> i) & 0x1;
  21. }
  22. set :: proc(x: ^T, cell, k: T, rule: u8) {
  23. x^ &~= 1<<cell;
  24. if rule>>k&1 != 0 {
  25. x^ |= 1<<cell;
  26. }
  27. }
  28. a := state;
  29. a1 := T(0);
  30. output(a);
  31. last := T(N-1);
  32. for r in 0..<generations {
  33. if pause > 0 do time.sleep(pause);
  34. k := bit(a, last) | bit(a, 0)<<1 | bit(a, 1)<<2;
  35. set(&a1, 0, k, rule);
  36. a1 |= (1<<0) * T(rule>>k&1);
  37. for c in 1..<last {
  38. k = k>>1 | bit(a, c+1)<<2;
  39. set(&a1, c, k, rule);
  40. }
  41. set(&a1, last, k>>1|bit(a, 0)<<2, rule);
  42. a, a1 = a1, a;
  43. output(a);
  44. if a == a1 {
  45. return;
  46. }
  47. }
  48. }
  49. main :: proc() {
  50. elementary_cellular_automata(
  51. state=rand.uint128(),
  52. rule=30,
  53. generations=5000,
  54. pause=100*time.Millisecond,
  55. );
  56. }