You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

114 lines
3.4 KiB

  1. # coding: utf-8 import os, sys
  2. from z3 import *
  3. # get the playground information
  4. if len(sys.argv) != 2:
  5. print("Usage: python3 colours.py <map-file>")
  6. sys.exit(0)
  7. with open(sys.argv[1]) as f:
  8. playground = f.read()
  9. playground = playground.strip().split("\n")
  10. # get the playground size
  11. size_y = len(playground)
  12. assert(size_y != 0)
  13. size_x = len(playground[0])
  14. assert(size_x != 0)
  15. assert(all([len(p) == size_x for p in playground]))
  16. # get the number of regions
  17. regions = set("".join(playground))
  18. ################################### Colours ####################################
  19. # create the solver
  20. solver = Solver()
  21. # todo: create a datatype Colour
  22. # ...
  23. # todo: declare four valid colours
  24. # ...
  25. # hint: don't forget to call "create" for the datatype to get a Sort
  26. # ...
  27. # todo: create a colour variable for each playground cell
  28. # hint: you can do this with Const("var_name", YourSort)
  29. # hint: use something like the coordinates as part of the variable name
  30. p_colours = [[None for _j in range(size_x)] for _j in range(size_y)]
  31. for i in range(size_y):
  32. for j in range(size_x):
  33. # p_colours[i][j] = ... replace this with your code
  34. pass
  35. print("All regions found in this map: '{}'.".format(",".join(regions)))
  36. for r in regions:
  37. # todo: find all cells that belong to the same region
  38. region_vars = []
  39. for i in range(size_y):
  40. for j in range(size_x):
  41. pass # ... add the variable to region_vars here
  42. # todo: make all colours in the same region identical
  43. # hint: use the transitivitiy of equality x1 = x2 & x2 = x3 -> x1 = x3
  44. for c in range(len(region_vars) - 1):
  45. pass # ... replace this with your code ...
  46. def get_neighbours(i, j):
  47. regions = []
  48. colours = []
  49. if i > 0:
  50. colours.append( p_colours[i-1][j])
  51. regions.append(playground[i-1][j])
  52. if i < size_y - 1:
  53. colours.append( p_colours[i+1][j])
  54. regions.append(playground[i+1][j])
  55. if j > 0:
  56. colours.append( p_colours[i][j-1])
  57. regions.append(playground[i][j-1])
  58. if j < size_x - 1:
  59. colours.append( p_colours[i][j+1])
  60. regions.append(playground[i][j+1])
  61. return zip(regions, colours)
  62. # todo: if two neighboring cells are from different regions
  63. # then they must have different colours
  64. for i in range(size_y):
  65. for j in range(size_x):
  66. cell_r = playground[i][j]
  67. cell_c = p_colours[i][j]
  68. for r, c in get_neighbours(i, j):
  69. pass # ... replace this with your code ...
  70. # call the solver and check satisfiability
  71. res = solver.check()
  72. if res != sat:
  73. print("unsat")
  74. sys.exit(1)
  75. # todo make a translation to strings "1", "2", "3", "4"
  76. def translate(s):
  77. # hint: do something analogouns to the following line here
  78. # if s.sexpr() == "C1": return "1"
  79. # ...
  80. return "0"
  81. ################################################################################
  82. from colorama import Fore, Back, Style
  83. cols = [Back.BLACK, Back.RED, Back.GREEN, Back.BLUE, Back.MAGENTA]
  84. cols = [Style.BRIGHT + Fore.WHITE + c for c in cols]
  85. # print the model as translated numbers
  86. m = solver.model()
  87. names = [x.name() for x in m.decls()]
  88. for i in range(size_y):
  89. row = ""
  90. for j in range(size_x):
  91. pc = p_colours[i][j]
  92. invalid = (pc is None or pc.decl() not in m.decls())
  93. t = "0" if invalid else translate(m[pc])
  94. if sys.stdout.isatty(): t = cols[int(t)] + t + Style.RESET_ALL
  95. row += t
  96. print(row)