50,782
社区成员
昨天自己写了一下 不会做 看了梗哥的题解 看懂了按思路写了一遍加了注释
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Scanner;
public class Main {
static Map<Integer,List<Integer>>map=new HashMap<>();//存放路径 每个数对应的前一个数的集合
static StringBuilder luxian=new StringBuilder();//存放最大地雷数路径
public static void main(String[] args) {
// TODO 自动生成的方法存根
Scanner sc=new Scanner(System.in);
int n=sc.nextInt();//地窖个数
int nums[]=new int[n+1];//不用下标0 地雷个数输入
for(int i=1;i<=n;i++) {
nums[i]=sc.nextInt();
}
while(true) {
int a=sc.nextInt();
int b=sc.nextInt();
if(a==0&&b==0)break;
add(b,a);
}
int path[]=new int[n+1];//存放当前地窖来自哪一个前面的地窖下标
int dp[]=new int[n+1];//从下标1开始 dp[i]表示以nums[i]结尾的最大地雷数
for(int i=1;i<=n;i++) {//base case
dp[i]=nums[i];//至少包括自己 base case
path[i]=i;//初始化 自己指向自己
}
for(int i=1;i<=n;i++) {//从小到大遍历下标
if(!map.containsKey(i))continue;//没有 通往当前下标i的路线
List<Integer>list=map.get(i);
for(int j:list) {//遍历所有路线 选择地雷数最大的那条路线
if(dp[i]<dp[j]+nums[i]) {
dp[i]=dp[j]+nums[i];
path[i]=j;//更新当前地窖来自前面地窖的路线
}
}
}
int res=0;//存放最大地雷数
int id=0;//存放 最大地雷数路线的终点 便于回溯寻找路线
for(int i=1;i<=n;i++) {//遍历dp数组 寻找最大地雷数
if(dp[i]>res) {
res=dp[i];
id=i;
}
}
recur(path,id);
luxian.deleteCharAt(luxian.length()-1);//去掉最后的"-"
System.out.println(luxian);
System.out.print(res);
}
private static void add(int a, int b) {
if(!map.containsKey(a))map.put(a,new ArrayList<>());
map.get(a).add(b);
}
private static void recur(int path[],int id) {//回溯寻找路线
if(id==path[id]) {//起点一定指向自己
luxian.append(id);//加起点
luxian.append("-");
return;
}
recur(path,path[id]);
luxian.append(id);
luxian.append("-");
}
}