Advertisement
Guest User

Untitled

a guest
Mar 22nd, 2019
51
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 5.46 KB | None | 0 0
  1. #include <iostream>
  2. #include <vector>
  3. #include <queue>
  4. #include <set>
  5. #include <algorithm>
  6. #include <map>
  7.  
  8.  
  9. struct State {
  10. std::vector<int> arr;
  11. int prev = -1;
  12. char movement = ' ';
  13. int number = 0;
  14. int d = -1;
  15. State() { arr.resize(16); }
  16. };
  17.  
  18. void move_left(State &s1, State &s2, int curnum) {
  19. int i;
  20. for (i = 0; i < 16; ++i) {
  21. if (s1.arr[i] == 0)
  22. break;
  23. }
  24. for (int j = 0; j < 16; ++j) {
  25. if (j == i)
  26. s2.arr[j] = s1.arr[i - 1];
  27. else if (j == i - 1)
  28. s2.arr[j] = 0;
  29. else
  30. s2.arr[j] = s1.arr[j];
  31. }
  32. s2.movement = 'L';
  33. s2.prev = s1.number;
  34. s2.number = curnum;
  35. }
  36.  
  37. void move_right(State &s1, State &s2, int curnum) {
  38. int i;
  39. for (i = 0; i < 16; ++i) {
  40. if (s1.arr[i] == 0)
  41. break;
  42. }
  43. for (int j = 0; j < 16; ++j) {
  44. if (j == i)
  45. s2.arr[j] = s1.arr[i + 1];
  46. else if (j == i + 1)
  47. s2.arr[j] = 0;
  48. else
  49. s2.arr[j] = s1.arr[j];
  50. }
  51. s2.movement = 'R';
  52. s2.prev = s1.number;
  53. s2.number = curnum;
  54. }
  55.  
  56. void move_up(State &s1, State &s2, int curnum) {
  57. int i;
  58. for (i = 0; i < 16; ++i) {
  59. if (s1.arr[i] == 0)
  60. break;
  61. }
  62. for (int j = 0; j < 16; ++j) {
  63. if (j == i)
  64. s2.arr[j] = s1.arr[i - 4];
  65. else if (j == i - 4)
  66. s2.arr[j] = 0;
  67. else
  68. s2.arr[j] = s1.arr[j];
  69. }
  70. s2.movement = 'U';
  71. s2.prev = s1.number;
  72. s2.number = curnum;
  73. }
  74.  
  75. void move_down(State &s1, State &s2, int curnum) {
  76. int i;
  77. for (i = 0; i < 16; ++i) {
  78. if (s1.arr[i] == 0)
  79. break;
  80. }
  81. for (int j = 0; j < 16; ++j) {
  82. if (j == i)
  83. s2.arr[j] = s1.arr[i + 4];
  84. else if (j == i + 4)
  85. s2.arr[j] = 0;
  86. else
  87. s2.arr[j] = s1.arr[j];
  88. }
  89. s2.movement = 'D';
  90. s2.prev = s1.number;
  91. s2.number = curnum;
  92. }
  93.  
  94. class Compare {
  95. public:
  96. bool operator()(const std::vector<int> &a, const std::vector<int> &b) {
  97. for (int i = 0; i < 16; ++i)
  98. if (a[i] < b[i])
  99. return true;
  100. else if (a[i] > b[i])
  101. return false;
  102. return false;
  103. }
  104. };
  105.  
  106. bool check_if_right(State &s) {
  107. for (int i = 0; i < 15; ++i)
  108. if (s.arr[i] != i + 1)
  109. return false;
  110. return true;
  111. }
  112.  
  113. int count_manhattan(State& s){
  114. int dest = 0;
  115. for( int i = 0; i < 16; ++i){
  116. dest += abs(s.arr[i] % 4 - i % 4) + abs(s.arr[i] / 4 - i / 4);
  117. }
  118. return dest;
  119. }
  120.  
  121. bool play(State &s0, std::vector<char> &strategy) {
  122. int curnum = 0;
  123. std::vector<State> positions;
  124. std::multimap<int, State> states;
  125. std::set<std::vector<int>, Compare> used;
  126. used.insert(s0.arr);
  127. states.emplace(0, s0);
  128. positions.push_back(s0);
  129. s0.number = curnum;
  130. ++curnum;
  131. while (!states.empty()) {
  132. State cur = states.begin()->second;
  133. if (check_if_right(cur)) {
  134. int pos = cur.number;
  135. while (pos != -1) {
  136. strategy.emplace_back(positions[pos].movement);
  137. pos = positions[pos].prev;
  138. }
  139. std::reverse(strategy.begin(), strategy.end());
  140. return true;
  141. }
  142. int i;
  143. for (i = 0; i < 16; ++i)
  144. if (cur.arr[i] == 0)
  145. break;
  146. if (i / 4 > 0) {
  147. State temp;
  148. move_up(cur, temp, curnum);
  149. if (used.find(temp.arr) == used.end()) {
  150. positions.push_back(temp);
  151. used.insert(temp.arr);
  152. temp.d = cur.d + 1;
  153. states.emplace(temp.d + count_manhattan(temp), temp);
  154. ++curnum;
  155. }
  156. }
  157. if (i / 4 < 3) {
  158. State temp;
  159. move_down(cur, temp, curnum);
  160. if (used.find(temp.arr) == used.end()) {
  161. positions.push_back(temp);
  162. used.insert(temp.arr);
  163. temp.d = cur.d + 1;
  164. states.emplace(temp.d + count_manhattan(temp), temp);
  165. ++curnum;
  166. }
  167. }
  168. if (i % 4 > 0) {
  169. State temp;
  170. move_left(cur, temp, curnum);
  171. if (used.find(temp.arr) == used.end()) {
  172. positions.push_back(temp);
  173. used.insert(temp.arr);
  174. temp.d = cur.d + 1;
  175. states.emplace(temp.d + count_manhattan(temp), temp);
  176. ++curnum;
  177. }
  178. }
  179. if (i % 4 < 3) {
  180. State temp;
  181. move_right(cur, temp, curnum);
  182. if (used.find(temp.arr) == used.end()) {
  183. positions.push_back(temp);
  184. used.insert(temp.arr);
  185. temp.d = cur.d + 1;
  186. states.emplace(temp.d + count_manhattan(temp), temp);
  187. ++curnum;
  188. }
  189. }
  190. states.erase(states.begin());
  191. }
  192. return false;
  193. }
  194.  
  195. int main() {
  196. State s0;
  197. std::vector<char> strategy;
  198. int num = 0;
  199. for (int i = 0; i < 16; ++i) {
  200. std::cin >> num;
  201. s0.arr[i] = num;
  202. }
  203. bool mark = play(s0, strategy);
  204. if (mark) {
  205. std::cout << strategy.size() - 1 << std::endl;
  206. for (int i = 1; i < strategy.size(); ++i)
  207. std::cout << strategy[i];
  208. } else
  209. std::cout << -1;
  210. return 0;
  211. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement