-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathNumberOfIslands.php
123 lines (104 loc) · 2.89 KB
/
NumberOfIslands.php
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
<?php
namespace QueueAndStack\QueueFirstInFirstOut\NumberOfIslands;
// 给定一个由 '1'(陆地)和 '0'(水)组成的的二维网格,计算岛屿的数量。一个岛被水包围,并且它是通过水平方向或垂直方向上相邻的陆地连接而成的。你可以假设网格的四个边均被水包围。
//
// 示例 1:
//
// 输入:
// 11110
// 11010
// 11000
// 00000
//
// 输出: 1
// 示例 2:
//
// 输入:
// 11000
// 11000
// 00100
// 00011
//
// 输出: 3
class Solution
{
protected $xLength;
protected $yLength;
protected $visited;
protected $index = 0;
/**
* @param String[][] $grid
* @return Integer
*/
function numIslands($grid)
{
$this->visited = $grid;
$this->yLength = count($grid);
if (0 === $this->yLength) {
return -1;
}
$this->xLength = count($grid[0]);
$lands = 0;
for ($y = 0; $y < $this->yLength; ++$y) {
for ($x = 0; $x < $this->xLength; ++$x) {
// 如果当前这个值为 1, 且没有被遍历过,那么就算岛屿
if ($this->visited[$y][$x] == '1') {
++$lands;
$this->visited[$y][$x] = 0;
$this->BFS($x, $y);
}
}
}
return $lands;
}
/**
* 使用广度优先算法,每次迭代一个层级直到不顾和条件
* 假设岛屿是这样
* 1 1 0 0 0
* 1 1 1 1 0
* 1 0 1 0 0
* 1 0 0 0 1
*
* 那么 DFS 搜索的顺序是这样(假设递归的顺序是↑↓←→
* (总是先往同一个方向发展,直到尽头,然后尽头节点的第二个方向)
* (先后的顺序取决于代码中先递归哪一个方向)
* 1 6 0 0 0
* 2 5 7 9 0
* 3 0 8 0 0
* 4 0 0 0 1
*
* BFS 的搜索顺序则是(假设迭代的顺序是↑↓←→
* 1 3 0 0 0
* 2 5 7 9 0
* 4 0 8 0 0
* 6 0 0 0 1
*
* @param $x
* @param $y
*/
protected function BFS($x, $y)
{
$offset = [0, 1, 0, -1, 0];
// 待处理队列
$q = ["{$y}:{$x}"];
while (! empty($q)) {
$first = array_shift($q);
list($y, $x) = array_map('intval', explode(':', $first));
// 取到上下左右四个
for ($i = 0; $i < 4; ++$i) {
$currX = $x+$offset[$i];
$currY = $y+$offset[$i + 1];
if (
$currX >= 0 &&
$currX < $this->xLength &&
$currY >= 0 &&
$currY < $this->yLength &&
$this->visited[$currY][$currX] == '1'
) {
$this->visited[$currY][$currX] = '0';
$q[] = "{$currY}:{$currX}";
}
}
}
}
}