LCP 07. 传递信息
小朋友 A 在和 ta 的小伙伴们玩传信息游戏,游戏规则如下:
- 有 n 名玩家,所有玩家编号分别为 0 ~ n-1,其中小朋友 A 的编号为 0
- 每个玩家都有固定的若干个可传信息的其他玩家(也可能没有)。传信息的关系是单向的(比如 A 可以向 B 传信息,但 B 不能向 A 传信息)。
- 每轮信息必须需要传递给另一个人,且信息可重复经过同一个人
给定总玩家数 n,以及按 [玩家编号,对应可传递玩家编号] 关系组成的二维数组 relation。返回信息从小 A (编号 0 ) 经过 k 轮传递到编号为 n-1 的小伙伴处的方案数;若不能到达,返回 0。
比如:
输入:n = 5, relation = [[0,2],[2,1],[3,4],[2,3],[1,4],[2,0],[0,4]], k = 3
输出:3
解释:信息从小 A 编号 0 处开始,经 3 轮传递,到达编号 4。共有 3 种方案,分别是 0->2->0->4, 0->2->1->4, 0->2->3->4。
怎么求解?
-
先说思路
有很多解法,其中最快上手的肯定是DFS,很像全排列,一个个坐标穷举,递归走k-1次,看有几个到n-1位置就行
要点:
(1)二维数组要用数据结构处理下,避免每次都for循环On,最好处理成O1;
(2)DFS代码要很娴熟 -
代码
class Solution {
Map<Integer, Set<Integer>> map = new HashMap<>();
int result = 0;
public int numWays(int n, int[][] relation, int k) {
// 转化数据模型,方便取,不然每次都要遍历
for(int [] arr:relation ){
Set<Integer> set = map.getOrDefault(arr[0] , new HashSet<>());
set.add(arr[1]);
map.put(arr[0],set);
}
dfs(0,0,k,n);
return result;
}
void dfs(int current, int levels,int k,int n){
if(levels == k){
if(current == n-1) result++;
return;
}
// 当前节点能到达的位置
Set<Integer> set = map.get(current);
if(set == null) return;
for(int index : set){
dfs(index,levels+1,k,n);
}
}
}
学习要点:
- 处理二维数组的数据结构
Map<Integer,Set<Integer>>
绝了,key放当前位置坐标,Set放能走到的位置。 - DFS算法基础模型还是要好好训练下,很重要。