Given a non-empty 2D arraygridof 0's and 1's, an island is a group of1's (representing land) connected 4-directionally (horizontal or vertical.) You may assume all four edges of the grid are surrounded by water.
Count the number of distinct islands. An island is considered to be the same as another if and only if one island can be translated (and not rotated or reflected) to equal the other.
Example 1:
11000
11000
00011
00011
Given the above grid map, return1.
Example 2:
11011
10000
00001
11011
Given the above grid map, return3.
Notice that:
11
1
and
1
11
are considered different island shapes, because we do not consider reflection / rotation.
Note:The length of each dimension in the givengriddoes not exceed 50.
解法二:其实这个pattern,我们每次都得loop一遍所有找到得island来判断,这样比较低效。所以如果能生成一个unique的key的话,我们每次就只要去hashmap里看看,最后返回map的size就好了。那么怎么生成unique的key呢,其实,因为bfs的顺序是一样的从左上到右下,所以所有同款的island所包含的node加入到这个island的顺序是一样的。我们就用set of set来装。T:O(n*m), S:O(n * m)
classSolution {int n =0;int m =0;publicintnumDistinctIslands(int[][] grid) {if (grid ==null||grid.length==0|| grid[0].length==0) {return0; } n =grid.length; m = grid[0].length;boolean[][] visited =newboolean[n][m];Set<Set<Pair<Integer,Integer>>> islands =newHashSet<>();for (int i =0; i < n; i++) {for (int j =0; j < m; j++) {if (grid[i][j] ==0|| visited[i][j]) {continue; }Set<Pair<Integer,Integer>> nodesOfAIsland =newHashSet<>();findIsland(i, j, grid, visited, nodesOfAIsland);islands.add(nodesOfAIsland); } }returnislands.size(); }int[] x = {0,0,1,-1};int[] y = {1,-1,0,0}; private void findIsland(int i, int j, int[][] grid, boolean[][] visited, Set<Pair<Integer, Integer>> nodesOfAIsland) {
Queue<Integer> queue =newLinkedList<>(); queue.offer(i * m + j); visited[i][j] =true;while (!queue.isEmpty()) {int cur =queue.poll();int curi = cur / m;int curj = cur % m;nodesOfAIsland.add(newPair<>(curi - i, curj - j));for (int k =0; k <4; k++) {int nexti = curi + x[k];int nextj = curj + y[k];if (inBound(nexti, nextj)&&!visited[nexti][nextj] && grid[nexti][nextj] ==1) {queue.offer(nexti * m + nextj); visited[nexti][nextj] =true; } } } }privatebooleaninBound(int i,int j) {if (i <0|| j <0|| i >= n || j >= m) {returnfalse; }returntrue; }}