fork(1) download
  1. import java.awt.Point;
  2. import java.io.BufferedReader;
  3. import java.io.InputStreamReader;
  4. import java.util.HashMap;
  5. import java.util.HashSet;
  6. import java.util.Map;
  7. import java.util.Set;
  8. import java.util.StringTokenizer;
  9.  
  10. /** Google Code Jam 2013, wrong code for round 1B, problem B */
  11. class B {
  12.  
  13. public static void main(String[] args) throws Exception {
  14. init();
  15.  
  16. int T = Integer.parseInt(br.readLine());
  17. String line;
  18. for (int ii = 0; ii < T; ii++) {
  19. line = br.readLine();
  20. tok = new StringTokenizer(line);
  21. int N, X, Y;
  22. N = Integer.parseInt(tok.nextToken());
  23. X = Integer.parseInt(tok.nextToken());
  24. Y = Integer.parseInt(tok.nextToken());
  25. System.out.printf("Case #%d: %.9f\n", ii+1, solve(N, X, Y));
  26. }
  27. }
  28.  
  29. static HashMap<Integer, HashMap<Point, Double>> data = new HashMap<>();
  30.  
  31. public static void init() {
  32. HashMap<Point, Double> n1map = new HashMap<>();
  33. n1map.put(new Point(0, 0), 1D);
  34. data.put(1, n1map);
  35.  
  36. data.put(6, getN6());
  37.  
  38. data.put(15, getN15());
  39. }
  40.  
  41. private static HashMap<Point, Double> getN6() {
  42. HashMap<Point, Double> res = new HashMap<>();
  43. res.putAll(data.get(1));
  44. int x = -2;
  45. int y = 0;
  46. res.put(new Point(x, y), 1D);
  47. for (int i = 0; i < 2; i++) {
  48. ++x;
  49. ++y;
  50. res.put(new Point(x, y), 1D);
  51. }
  52. for (int i = 0; i < 2; i++) {
  53. ++x;
  54. --y;
  55. res.put(new Point(x, y), 1D);
  56. }
  57. return res;
  58. }
  59.  
  60. private static HashMap<Point, Double> getN15() {
  61. HashMap<Point, Double> res = new HashMap<>();
  62. res.putAll(data.get(6));
  63. int x = -4;
  64. int y = 0;
  65. res.put(new Point(x, y), 1D);
  66. for (int i = 0; i < 3; i++) {
  67. ++x;
  68. ++y;
  69. res.put(new Point(x, y), 1D);
  70. }
  71. for (int i = 0; i < 3; i++) {
  72. ++x;
  73. --y;
  74. res.put(new Point(x, y), 1D);
  75. }
  76. return res;
  77. }
  78.  
  79. public static double solve(int N, int X, int Y) {
  80. Set<Integer> special = new HashSet<Integer>(); special.add(1); special.add(6); special.add(15);
  81. HashMap<Point, Double> map;
  82. if (special.contains(N)) {
  83. map = data.get(N);
  84. } else {
  85. if (data.containsKey(N)) {
  86. map = data.get(N);
  87. } else {
  88. if (N > 15) {
  89. map = get(15, N - 15, 6);
  90. } else if (N > 6 ) {
  91. map = get(6, N - 6, 4);
  92. } else {
  93. map = get(1, N - 1, 2);
  94. }
  95. data.put(N, map);
  96. }
  97. }
  98. Double res = map.get(new Point(X, Y));
  99. return res == null ? 0 : res;
  100. }
  101.  
  102. private static HashMap<Point, Double> get(int SN, int cnt, int max) {
  103. // SN = special N
  104. HashMap<Point, Double> res = new HashMap<>();
  105. int pos = 0;
  106. for (int mask = 0; mask < (1 << cnt); mask++) {
  107. int rc = Integer.bitCount(mask);
  108. int lc = cnt - rc;
  109. if (rc > max || lc > max ) {
  110. continue;
  111. }
  112. ++pos;
  113. for (int i = 0; i < lc; i++) {
  114. Point p = getLeft(SN, i);
  115. inc(p, res);
  116. }
  117. for (int i = 0; i < rc; i++) {
  118. Point p = getRight(SN, i);
  119. inc(p, res);
  120. }
  121. }
  122. // divide by pos
  123. //System.out.printf( "DEBUG: pos=%d\n", pos );
  124. for (Point p : res.keySet()) {
  125. double prob = res.get(p);
  126. res.put(p, prob / pos);
  127. }
  128. // add special points
  129. res.putAll(data.get(SN));
  130. return res;
  131. }
  132.  
  133. private static Point getLeft(int SN, int idx) {
  134. int y = 0;
  135. int x;
  136. switch(SN) {
  137. case 1: x = -2; break;
  138. case 6: x = -4; break;
  139. case 15: x = -6; break;
  140. default: throw new IllegalArgumentException("SN=" + SN);
  141. }
  142. for (int i = 0; i < idx; i++) {
  143. ++y;
  144. ++x;
  145. }
  146. return new Point(x, y);
  147. }
  148.  
  149. private static Point getRight(int SN, int idx) {
  150. int y = 0;
  151. int x;
  152. switch(SN) {
  153. case 1: x = 2; break;
  154. case 6: x = 4; break;
  155. case 15: x = 6; break;
  156. default: throw new IllegalArgumentException("SN=" + SN);
  157. }
  158. for (int i = 0; i < idx; i++) {
  159. ++y;
  160. --x;
  161. }
  162. return new Point(x, y);
  163. }
  164.  
  165. private static void inc(Point p, Map<Point, Double> map) {
  166. Double val = map.get(p);
  167. if (val == null) val = 0D;
  168. map.put(p, val + 1);
  169. }
  170.  
  171. }
  172.  
Success #stdin #stdout 0.07s 380160KB
stdin
7
1 0 0
1 0 2
3 0 0
3 2 0
3 1 1
4 1 1
4 0 2
stdout
Case #1: 1.000000000
Case #2: 0.000000000
Case #3: 1.000000000
Case #4: 0.750000000
Case #5: 0.250000000
Case #6: 0.500000000
Case #7: 0.000000000