HackerRank: Coin on the Table


HackerRank: Coin on the Table
You have a rectangular board consisting of N rows, numbered from 1 to N, and M columns, numbered from 1 to M. The top left is (1,1) and the bottom right is (N,M). Initially - at time 0 - there is a coin on the top-left cell of your board. Each cell of your board contains one of these letters:

*: Exactly one of your cells has letter '*'.

U: If at time t, the coin is on the cell(i,j) and cell(i,j) has letter 'U', the coin will be on the cell(i-1,j) in time t+1, if i > 1. Otherwise there is no coin on your board at time t+1.

L: If at time t, the coin is on the cell(i,j) and cell(i,j) has letter 'L', the coin will be on the cell(i,j-1) in time t+1, if j > 1. Otherwise there is no coin on your board at time t+1.

D: If at time t, the coin is on the cell(i,j) and cell(i,j) has letter 'D', the coin will be on the cell(i+1,j) in time t+1, if i < N. Otherwise there is no coin on your board at time t+1.

R: If at time t, the coin is on the cell(i,j) and cell(i,j) has letter 'R', the coin will be on the cell(i,j+1) in time t+1, if j < M. Otherwise there is no coin on your board at time t+1.

When the coin reaches a cell that has letter '*', it will stay there permanently. When you punch on your board, your timer starts and the coin moves between cells. Before starting the game, you can make operations to change the board, such that, you are sure that at time K the coin will reach the cell having letter '*'. In each operation you can select a cell with some letter other than '*' and change the letter to 'U', 'L', 'R' or 'D'. You need to carry out as few operations as possible in order to achieve your goal. Your task is to find the minimum number of operations.

BFS:
  cost = new int[N][M];
  for (int i = 0; i < N; i++)
   // for (int j = 0; j < M; j++)
   Arrays.fill(cost[i], Integer.MAX_VALUE);

  int ret = bfs(k);
  if (ret == Integer.MAX_VALUE)
   ret = -1;

  System.out.println(ret);

 class Node implements Comparable<Node> {
 public int x;
 public int y;
 public int k;
 public int cost; }

 private int bfs(int K) {
  Queue<Node> queue = new PriorityQueue<Node>();
  queue.add(new Node(0, 0, K, 0));
  while (!queue.isEmpty()) {
   Node node = queue.poll();
   int x = node.x;
   int y = node.y;
   int k = node.k;
   int cost = node.cost;

   this.cost[x][y] = Math.min(this.cost[x][y], cost);
   if (board[x].charAt(y) == '*' && k >= 0)
    return this.cost[x][y];
   else if (k < 0)
    continue;

   for (int i = 0; i < 4; i++) {
    int xx = x + dx[i];
    int yy = y + dy[i];
    if (inBoard(xx, yy)) {
     int c = board[x].charAt(y) == ch[i] ? 0 : 1;
     if (c + cost < this.cost[xx][yy])
      queue.add(new Node(xx, yy, k - 1, c + cost));
    }
   }
  }
  return -1;
 }

 private boolean inBoard(int x, int y) {
  return x >= 0 && x < N && y >= 0 && y < M;
 }
}

DFS:
https://github.com/derekhh/HackerRank/blob/master/coin-on-the-table.cpp
http://fenghaolw.blogspot.com/2014/01/coin-on-table.html
char map[52][52];
int best[52][52][1001];
int n, m, k;

void update(int row, int col, int time, int val)
{
if (row < 0 || row >= n) return;
if (col < 0 || col >= m) return;
if (time > k) return;

if (val < best[row][col][time] || best[row][col][time] == -1)
{
best[row][col][time] = val;

if (map[row][col] != '*')
{
update(row, col + 1, time + 1, val + (map[row][col] != 'R'));
update(row, col - 1, time + 1, val + (map[row][col] != 'L'));
update(row - 1, col, time + 1, val + (map[row][col] != 'U'));
update(row + 1, col, time + 1, val + (map[row][col] != 'D'));
}
else
{
update(row, col, time + 1, val);
}
}
}

int main()
{
cin >> n >> m >> k;
int r, c;
for (int i = 0; i < n; i++)
for (int j = 0; j < m; j++)
{
cin >> map[i][j];
if (map[i][j] == '*')
r = i, c = j;
}
memset(best, -1, sizeof(best));
update(0, 0, 0, 0);
cout << best[r][c][k] << endl;
return 0;
}

Time Complexity: O(NMK)
Required Knowledge: DP
Also check http://www.cnblogs.com/sunshineatnoon/p/3919423.html
A DP solution is not hard to come up with. Let `f(i,j,k)` denote the minimum # of letter replacement we have to make to arrive cell `(i,j)` starting from `(1,1)` at time `k`. Then, the recurrence simply looks like `
f(i,j,k)=0minf(i1,j,k1)+δ(i1,j,i,j)f(i+1,j,k1)+δ(i+1,j,i,j)f(i,j1,k1)+δ(i,j1,i,j)f(i,j+1,k1)+δ(i,j+1,i,j)if i=1j=1 and k=0if (i1 or j1) and k=0if i<1, or i>N, or j<1, or j>Mif k>0 ,
` where `δ(i,j,x,y)=0` if the letter in cell `(i,j)` is the right one that leads to cell `(x,y)`, and `δ(i,j,x,y)=1` otherwise. The answer to this problem is simply `
mini=0Kf(N,M,i).
` If that value is `` then just output `1`. If you have some concerns about this expression, please read the following sentence carefully.

When the coin reaches a cell that has letter *, it will stay there permanently
So why it is correct? Seems like the DP approach above may potentially change the letter of some cell more than once. However, it is easy to observe that, for any cell `(i,j)`, it will only be visited at most once in any optimal solution; otherwise, a cycle will be formed, and removing that cycle will clearly result in a better solution. So, even though we may change some letter more than once for some state, this state will always be beaten or never used in the future, thus can never contribute to our final output.

public static void main(String[] args) {
        Scanner cin = new Scanner(System.in);

        int n = cin.nextInt();
        int m = cin.nextInt();
        int K = cin.nextInt();
        int x = 0, y = 0;
        char a[][] = new char[n][];
        for (int i=0; i<n; i++) {
            a[i] = cin.next().toCharArray();
            for (int j=0; j<m; j++)
                if (a[i][j] == '*') {
                    x = i;
                    y = j;
                }
        }


        int f[][][] = new int[K + 1][n][m];
        int ans = 1 << 29;
        for (int k=0; k<=K; k++)
            for (int i=0; i<n; i++)
                for (int j=0; j<m; j++) 
                    if (k == 0) f[k][i][j] = i == 0 && j == 0 ? 0 : 1 << 29;
                    else {
                        int res = 1 << 29;
                        if (i > 0)     res = Math.min(res, f[k - 1][i - 1][j] + (a[i - 1][j] == 'D' ? 0 : 1));
                        if (i < n - 1) res = Math.min(res, f[k - 1][i + 1][j] + (a[i + 1][j] == 'U' ? 0 : 1));
                        if (j > 0)     res = Math.min(res, f[k - 1][i][j - 1] + (a[i][j - 1] == 'R' ? 0 : 1));
                        if (j < m - 1) res = Math.min(res, f[k - 1][i][j + 1] + (a[i][j + 1] == 'L' ? 0 : 1));

                        f[k][i][j] = res;
                    }

        for (int k=0; k<=K; k++)
            ans = Math.min(ans, f[k][x][y]);

        if (ans < (1 << 29)) System.out.println(ans);
        else System.out.println(-1);

        cin.close();
    }

https://codepair.hackerrank.com/paper/gI7bCSVm?b=eyJyb2xlIjoiY2FuZGlkYXRlIiwibmFtZSI6ImplZmZlcnl5dWFuIiwiZW1haWwiOiJ5dWFueXVuLmtlbm55QGdtYWlsLmNvbSJ9

Labels

LeetCode (1432) GeeksforGeeks (1122) LeetCode - Review (1067) Review (882) Algorithm (668) to-do (609) Classic Algorithm (270) Google Interview (237) Classic Interview (222) Dynamic Programming (220) DP (186) Bit Algorithms (145) POJ (141) Math (137) Tree (132) LeetCode - Phone (129) EPI (122) Cracking Coding Interview (119) DFS (115) Difficult Algorithm (115) Lintcode (115) Different Solutions (110) Smart Algorithm (104) Binary Search (96) BFS (91) HackerRank (90) Binary Tree (86) Hard (79) Two Pointers (78) Stack (76) Company-Facebook (75) BST (72) Graph Algorithm (72) Time Complexity (69) Greedy Algorithm (68) Interval (63) Company - Google (62) Geometry Algorithm (61) Interview Corner (61) LeetCode - Extended (61) Union-Find (60) Trie (58) Advanced Data Structure (56) List (56) Priority Queue (53) Codility (52) ComProGuide (50) LeetCode Hard (50) Matrix (50) Bisection (48) Segment Tree (48) Sliding Window (48) USACO (46) Space Optimization (45) Company-Airbnb (41) Greedy (41) Mathematical Algorithm (41) Tree - Post-Order (41) ACM-ICPC (40) Algorithm Interview (40) Data Structure Design (40) Graph (40) Backtracking (39) Data Structure (39) Jobdu (39) Random (39) Codeforces (38) Knapsack (38) LeetCode - DP (38) Recursive Algorithm (38) String Algorithm (38) TopCoder (38) Sort (37) Introduction to Algorithms (36) Pre-Sort (36) Beauty of Programming (35) Must Known (34) Binary Search Tree (33) Follow Up (33) prismoskills (33) Palindrome (32) Permutation (31) Array (30) Google Code Jam (30) HDU (30) Array O(N) (29) Logic Thinking (29) Monotonic Stack (29) Puzzles (29) Code - Detail (27) Company-Zenefits (27) Microsoft 100 - July (27) Queue (27) Binary Indexed Trees (26) TreeMap (26) to-do-must (26) 1point3acres (25) GeeksQuiz (25) Merge Sort (25) Reverse Thinking (25) hihocoder (25) Company - LinkedIn (24) Hash (24) High Frequency (24) Summary (24) Divide and Conquer (23) Proof (23) Game Theory (22) Topological Sort (22) Lintcode - Review (21) Tree - Modification (21) Algorithm Game (20) CareerCup (20) Company - Twitter (20) DFS + Review (20) DP - Relation (20) Brain Teaser (19) DP - Tree (19) Left and Right Array (19) O(N) (19) Sweep Line (19) UVA (19) DP - Bit Masking (18) LeetCode - Thinking (18) KMP (17) LeetCode - TODO (17) Probabilities (17) Simulation (17) String Search (17) Codercareer (16) Company-Uber (16) Iterator (16) Number (16) O(1) Space (16) Shortest Path (16) itint5 (16) DFS+Cache (15) Dijkstra (15) Euclidean GCD (15) Heap (15) LeetCode - Hard (15) Majority (15) Number Theory (15) Rolling Hash (15) Tree Traversal (15) Brute Force (14) Bucket Sort (14) DP - Knapsack (14) DP - Probability (14) Difficult (14) Fast Power Algorithm (14) Pattern (14) Prefix Sum (14) TreeSet (14) Algorithm Videos (13) Amazon Interview (13) Basic Algorithm (13) Codechef (13) Combination (13) Computational Geometry (13) DP - Digit (13) LCA (13) LeetCode - DFS (13) Linked List (13) Long Increasing Sequence(LIS) (13) Math-Divisible (13) Reservoir Sampling (13) mitbbs (13) Algorithm - How To (12) Company - Microsoft (12) DP - Interval (12) DP - Multiple Relation (12) DP - Relation Optimization (12) LeetCode - Classic (12) Level Order Traversal (12) Prime (12) Pruning (12) Reconstruct Tree (12) Thinking (12) X Sum (12) AOJ (11) Bit Mask (11) Company-Snapchat (11) DP - Space Optimization (11) Dequeue (11) Graph DFS (11) MinMax (11) Miscs (11) Princeton (11) Quick Sort (11) Stack - Tree (11) 尺取法 (11) 挑战程序设计竞赛 (11) Coin Change (10) DFS+Backtracking (10) Facebook Hacker Cup (10) Fast Slow Pointers (10) HackerRank Easy (10) Interval Tree (10) Limited Range (10) Matrix - Traverse (10) Monotone Queue (10) SPOJ (10) Starting Point (10) States (10) Stock (10) Theory (10) Tutorialhorizon (10) Kadane - Extended (9) Mathblog (9) Max-Min Flow (9) Maze (9) Median (9) O(32N) (9) Quick Select (9) Stack Overflow (9) System Design (9) Tree - Conversion (9) Use XOR (9) Book Notes (8) Company-Amazon (8) DFS+BFS (8) DP - States (8) Expression (8) Longest Common Subsequence(LCS) (8) One Pass (8) Quadtrees (8) Traversal Once (8) Trie - Suffix (8) 穷竭搜索 (8) Algorithm Problem List (7) All Sub (7) Catalan Number (7) Cycle (7) DP - Cases (7) Facebook Interview (7) Fibonacci Numbers (7) Flood fill (7) Game Nim (7) Graph BFS (7) HackerRank Difficult (7) Hackerearth (7) Inversion (7) Kadane’s Algorithm (7) Manacher (7) Morris Traversal (7) Multiple Data Structures (7) Normalized Key (7) O(XN) (7) Radix Sort (7) Recursion (7) Sampling (7) Suffix Array (7) Tech-Queries (7) Tree - Serialization (7) Tree DP (7) Trie - Bit (7) 蓝桥杯 (7) Algorithm - Brain Teaser (6) BFS - Priority Queue (6) BFS - Unusual (6) Classic Data Structure Impl (6) DP - 2D (6) DP - Monotone Queue (6) DP - Unusual (6) DP-Space Optimization (6) Dutch Flag (6) How To (6) Interviewstreet (6) Knapsack - MultiplePack (6) Local MinMax (6) MST (6) Minimum Spanning Tree (6) Number - Reach (6) Parentheses (6) Pre-Sum (6) Probability (6) Programming Pearls (6) Rabin-Karp (6) Reverse (6) Scan from right (6) Schedule (6) Stream (6) Subset Sum (6) TSP (6) Xpost (6) n00tc0d3r (6) reddit (6) AI (5) Abbreviation (5) Anagram (5) Art Of Programming-July (5) Assumption (5) Bellman Ford (5) Big Data (5) Code - Solid (5) Code Kata (5) Codility-lessons (5) Coding (5) Company - WMware (5) Convex Hull (5) Crazyforcode (5) DFS - Multiple (5) DFS+DP (5) DP - Multi-Dimension (5) DP-Multiple Relation (5) Eulerian Cycle (5) Graph - Unusual (5) Graph Cycle (5) Hash Strategy (5) Immutability (5) Java (5) LogN (5) Manhattan Distance (5) Matrix Chain Multiplication (5) N Queens (5) Pre-Sort: Index (5) Quick Partition (5) Quora (5) Randomized Algorithms (5) Resources (5) Robot (5) SPFA(Shortest Path Faster Algorithm) (5) Shuffle (5) Sieve of Eratosthenes (5) Strongly Connected Components (5) Subarray Sum (5) Sudoku (5) Suffix Tree (5) Swap (5) Threaded (5) Tree - Creation (5) Warshall Floyd (5) Word Search (5) jiuzhang (5)

Popular Posts