这道题和 1018 Public Bike Management(题解)解题思路上是一样的。
使用dfs从根结点开始搜索,使用temppath记录路径,如果之前经过的结点的权值总和加上当前访问的结点的权值之和恰好等于目标权值并且当前结点为叶节点,则将temppath记录下来( paths.push_back(temppath) ),最后对paths进行排序,注意排序函数的书写,严格按照题目中给的排序规则写。
本题的主要难点就在于路径的记录,具体实现见代码,注意push_back,pop_back的使用。
代码:
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
int N,M,T,k,node,temp;
int weight[105];
vector<int> G[105];
vector<vector<int> > paths;
vector<int> temppath;
bool cmp(vector<int>& v1,vector<int>& v2)
{
int len = min(v1.size(),v2.size());
for(int i = 0;i < len; i++)
{
if(v1[i] > v2[i])
return true;
else if(v1[i] < v2[i])
return false;
}
return false;
}
void dfs(int id,int curr_weight)
{
temppath.push_back(weight[id]);
if(curr_weight + weight[id] == T && G[id].size() == 0) // 权值和恰好等于T,且为叶节点
paths.push_back(temppath);
else if(curr_weight + weight[id] < T)
{
for(int i = 0;i < G[id].size(); i++)
dfs(G[id][i],curr_weight + weight[id]);
}
temppath.pop_back();
}
int main(int argc, char const *argv[])
{
cin >> N >> M >> T;
for(int i = 0;i < N; i++)
cin >> weight[i];
for(int i = 0;i < M; i++)
{
cin >> node >> k;
for(int j = 0;j < k; j++)
{
cin >> temp;
G[node].push_back(temp);
}
}
dfs(0,0);
sort(paths.begin(),paths.end(),cmp);
for(int i = 0;i < paths.size(); i++)
{
for(int j = 0;j < paths[i].size(); j++)
{
cout << paths[i][j] ;
if(j != paths[i].size()-1)
cout << " ";
}
cout << endl;
}
return 0;
}