This commit is contained in:
Chenxue3
2024-01-16 01:37:41 +13:00
4 changed files with 160 additions and 65 deletions

View File

@ -425,8 +425,8 @@ public:
if (needle.size() == 0) {
return 0;
}
int next[needle.size()];
getNext(next, needle);
vector<int> next(needle.size());
getNext(&next[0], needle);
int j = -1; // // 因为next数组里记录的起始位置为-1
for (int i = 0; i < haystack.size(); i++) { // 注意i就从0开始
while(j >= 0 && haystack[i] != needle[j + 1]) { // 不匹配
@ -524,8 +524,8 @@ public:
if (needle.size() == 0) {
return 0;
}
int next[needle.size()];
getNext(next, needle);
vector<int> next(needle.size());
getNext(&next[0], needle);
int j = 0;
for (int i = 0; i < haystack.size(); i++) {
while(j > 0 && haystack[i] != needle[j]) {
@ -1428,4 +1428,3 @@ public int[] GetNext(string needle)
<a href="https://programmercarl.com/other/kstar.html" target="_blank">
<img src="../pics/网站星球宣传海报.jpg" width="1000"/>
</a>

View File

@ -285,6 +285,34 @@ class Solution:
### Go
```go
/**
* @date: 2024 Jan 06
* @time: 13:44
* @author: Chris
**/
// 贪心算法优化版
// 记录步骤规则:每超过上一次可达最大范围,需要跳跃一次,次数+1
// 记录位置i == lastDistance + 1
func jump(nums []int) int {
// 根据题目规则初始位置为nums[0]
lastDistance := 0 // 上一次覆盖范围
curDistance := 0 // 当前覆盖范围(可达最大范围)
minStep := 0 // 记录最少跳跃次数
for i := 0; i < len(nums); i++ {
if i == lastDistance+1 { // 在上一次可达范围+1的位置记录步骤
minStep++ // 跳跃次数+1
lastDistance = curDistance // 记录时才可以更新
}
curDistance = max(nums[i]+i, curDistance) // 更新当前可达的最大范围
}
return minStep
}
```
```go
// 贪心版本一
func jump(nums []int) int {

View File

@ -389,50 +389,41 @@ function numIslands(grid: string[][]): number {
### Go
```go
var DIRECTIONS = [4][2]int{{-1, 0}, {0, -1}, {1, 0}, {0, 1}}
func numIslands(grid [][]byte) int {
// 用1标记已访问
visited := make([][]int, len(grid))
for i := 0; i < len(visited); i++{
visited[i] = make([]int, len(grid[0]))
}
res := 0
var bfs func(x, y int)
bfs = func(x, y int){
stack := make([][]int, 0)
stack = append(stack, []int{x, y})
moveX := []int{1, -1, 0, 0}
moveY := []int{0, 0, 1, -1}
visited := make([][]bool, len(grid))
for i := 0; i < len(grid); i++ {
visited[i] = make([]bool, len(grid[0]))
}
for len(stack) != 0{
node := stack[len(stack) - 1]
stack = stack[:len(stack) - 1]
for i, rows := range grid {
for j, v := range rows {
if v == '1' && !visited[i][j] {
res++
dfs(grid, visited, i, j)
}
}
}
for i := 0; i < 4; i++{
dx := moveX[i] + node[0]
dy := moveY[i] + node[1]
if dx < 0 || dx >= len(grid) || dy < 0 || dy >= len(grid[0]) || visited[dx][dy] == 1{
continue
}
visited[dx][dy] = 1
if grid[dx][dy] == '1'{
stack = append(stack, []int{dx,dy})
}
}
}
}
return res
}
result := 0
for i := 0; i < len(grid); i++{
for j := 0; j < len(grid[0]); j++{
if visited[i][j] == 0 && grid[i][j] == '1'{
bfs(i, j)
visited[i][j] = 1
result++
}
}
}
func dfs(grid [][]byte, visited [][]bool, i, j int) {
visited[x][y] = true
for _, d := range DIRECTIONS {
x, y := i+d[0], j+d[1]
if x < 0 || x >= len(grid) || y < 0 || y >= len(grid[0]) {
continue
}
if grid[x][y] == '1' && !visited[x][y] {
dfs(grid, visited, x, y)
}
}
return result
}
```

View File

@ -4,30 +4,28 @@
</a>
<p align="center"><strong><a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
# 1971. 寻找图中是否存在路径
# 1971. 寻找图中是否存在路径
[题目链接](https://leetcode.cn/problems/find-if-path-exists-in-graph/)
有一个具有 n个顶点的 双向 图,其中每个顶点标记从 0 到 n - 1包含 0 和 n - 1。图中的边用一个二维整数数组 edges 表示,其中 edges[i] = [ui, vi] 表示顶点 ui 和顶点 vi 之间的双向边。 每个顶点对由 最多一条 边连接,并且没有顶点存在与自身相连的边。
有一个具有 n 个顶点的 双向 图,其中每个顶点标记从 0 到 n - 1包含 0 和 n - 1。图中的边用一个二维整数数组 edges 表示,其中 edges[i] = [ui, vi] 表示顶点 ui 和顶点 vi 之间的双向边。 每个顶点对由 最多一条 边连接,并且没有顶点存在与自身相连的边。
请你确定是否存在从顶点 start 开始,到顶点 end 结束的 有效路径 。
给你数组 edges 和整数 n、startend如果从 start 到 end 存在 有效路径 ,则返回 true否则返回 false 。
![](https://code-thinking-1253855093.file.myqcloud.com/pics/20220705101442.png)
给你数组 edges 和整数 n、startend如果从 start 到 end 存在 有效路径 ,则返回 true否则返回 false 。
![](https://code-thinking-1253855093.file.myqcloud.com/pics/20220705101442.png)
提示:
* 1 <= n <= 2 * 10^5
* 0 <= edges.length <= 2 * 10^5
* edges[i].length == 2
* 0 <= ui, vi <= n - 1
* ui != vi
* 0 <= start, end <= n - 1
* 不存在双向边
* 不存在指向顶点自身的边
- 1 <= n <= 2 \* 10^5
- 0 <= edges.length <= 2 \* 10^5
- edges[i].length == 2
- 0 <= ui, vi <= n - 1
- ui != vi
- 0 <= start, end <= n - 1
- 不存在双向边
- 不存在指向顶点自身的边
## 思路
@ -70,7 +68,7 @@ void join(int u, int v) {
}
```
以上模板中,只要修改 n 大小就可以,本题n不会超过2 * 10^5。
以上模板中,只要修改 n 大小就可以,本题 n 不会超过 2 \* 10^5。
并查集主要有三个功能。
@ -80,17 +78,17 @@ void join(int u, int v) {
简单介绍并查集之后,我们再来看一下这道题目。
为什么说这道题目是并查集基础题目,题目中各个点是双向图链接,那么判断 一个顶点到另一个顶点有没有有效路径其实就是看这两个顶点是否在同一个集合里。
为什么说这道题目是并查集基础题目,题目中各个点是双向图链接,那么判断 一个顶点到另一个顶点有没有有效路径其实就是看这两个顶点是否在同一个集合里。
如何算是同一个集合呢,有边连在一起,就算是一个集合。
如何算是同一个集合呢,有边连在一起,就算是一个集合。
此时我们就可以直接套用并查集模板。
此时我们就可以直接套用并查集模板。
使用join(int u, int v)将每条边加入到并查集。
使用 join(int u, int v)将每条边加入到并查集。
最后 isSame(int u, int v) 判断是否是同一个根 就可以了。
最后 isSame(int u, int v) 判断是否是同一个根 就可以了。
C++代码如下:
C++代码如下:
```CPP
class Solution {
@ -191,7 +189,7 @@ class Solution {
### Python
PYTHON并查集解法如下
PYTHON 并查集解法如下:
```PYTHON
class Solution:
@ -206,6 +204,85 @@ class Solution:
return find(source) == find(destination)
```
### Javascript
Javascript 并查集解法如下:
```Javascript
class unionF{
constructor(n){
this.count = n
this.roots = new Array(n).fill(0).map((item,index)=>index)
}
findRoot(x){
if(this.roots[x]!==x){
this.roots[x] = this.findRoot(this.roots[x])
}
return this.roots[x]
}
union(x,y){
const rx = this.findRoot(x)
const ry = this.findRoot(y)
this.roots[rx] = ry
this.count--
}
isConnected(x,y){
return this.findRoot(x)===this.findRoot(y)
}
}
var validPath = function(n, edges, source, destination) {
const UF = new unionF(n)
for(const [s,t] of edges){
UF.union(s,t)
}
return UF.isConnected(source,destination)
};
```
Javascript 双向 bfs 解法如下:
```Javascript
var validPath = function(n, edges, source, destination) {
const graph = new Array(n).fill(0).map(()=>[])
for(const [s,t] of edges){
graph[s].push(t)
graph[t].push(s)
}
const visited = new Array(n).fill(false)
function bfs(start,end,graph){
const startq = [start]
const endq = [end]
while(startq.length&&endq.length){
const slen = startq.length
for(let i = 0;i<slen;i++){
const scur = startq.shift()
if(visited[scur]) continue
if(endq.includes(scur)) return true
visited[scur] = true
const neighbors = graph[scur]
startq.push(...neighbors)
}
const elen = endq.length
for(let i = 0;i<elen;i++){
const ecur = endq.shift()
if(visited[ecur]) continue
if(startq.includes(ecur)) return true
visited[ecur] = true
const neighbors = graph[ecur]
endq.push(...neighbors)
}
}
return false
}
return bfs(source,destination,graph)
};
```
<p align="center">
<a href="https://programmercarl.com/other/kstar.html" target="_blank">