2016华为软件精英挑战赛初赛题目,个人分析与代码,尚未测试代码,因为没有judge系统啊!
来源:互联网 发布:德国拜发测毒素软件 编辑:程序博客网 时间:2024/06/05 08:41
看到题目,首先想到这是一个哈密顿回路的题,但是不是简单的哈密顿回路,因为题目中要求走过的点不是所有点,而是所有点V的一个子集V',所以在求出一个到达终点的路径之后,做一个判断,看path是否经历过所有的V'就行了,而不需要像求哈密顿回路一样,去设置一个数字cur,当cur==V个数时才判断是否能到达终点。
哈密顿回路是np问题,目前比较直观的解法是采用dfs。
因此这道题目对dfs做了考察,另外,题目的输入输出非常繁琐,没有采用空格分割,而是逗号分割,并且还要人写到文件里面去,不是直接输入,这跟我做过这几年ACM题目都不同,先来回顾一下文件的读取方法:
ifstream a("1.csv");if(!a){return;}while(true){int b;char c;a>>b>>c;}
我们这里b是int型的,c是char型的,那么读取过程就会直接从文件先读取一个int型,再读取一个char型,本题输入的时候也是一个int,一个char,所以采用这个方法就可以了。
再来看题目本身,这个题目输入的是边的信息,而不是图的信息,因为两个点之间可以有多条路径,因此,我们遍历的是边,而不是点。
设置一个path[]数组,数组记录的是这次遍历过程经过的点,设置一个dist变量,记录这次遍历总共已经走过的长度。
通过dfs搜索,但是不以已经搜索点数等于V‘点数截至,而是一直搜索下去,当发现一个线终点是目标重点,则开始计算路径长度,并判断是否全部经过了V’如果路径长度是已知最短的,并且全部经过了V'的点,则更新successPath为当前path,直到遍历完全部情况。
这里有个小剪枝,如果当前path中储存的点数小于V'中的点数,则当发现一条边的终点是所求终点时也不需要进行判断,因为肯定不符合要求。
这种求法非常暴力,因为剪枝太少,但是毕竟是np问题,系统给出的时间是10s就可以看出其复杂程度,
这题肯定还有更多可以剪枝的部分,大家都可以想一想,说不定能拿个奖啊~
#include<iostream>#include<fstream>using namespace std;class line{public:int start;int end;int length;int id;};int pNum;int lNum;bool *ifVisited;bool ifVisitedLine[4801];int startP;int endP;int mustNum;int mustP[51];line l[4801];int path[4801];int successPath[51];int plength=999999;bool success;int pathPNum;void dfs(int cur){if(cur==pNum){return;}for(int i=1;i<=lNum;i++){if(l[i].start==l[path[cur]].end&&ifVisited[l[i].end]==false){if(l[i].end==endP){if(cur>=mustNum){for(int j=1;j<=mustNum;j++){if(ifVisited[j]==false){goto fall;}}int nowLength=0;for(int j=1;j<=cur;j++){nowLength=l[path[j]].length+nowLength;}if(nowLength<plength){plength=nowLength;pathPNum=cur;for(int j=1;j<cur;j++){successPath[j]=path[j];}goto success;}}else{fall:continue;}}else{path[cur]==l[i].id; ifVisited[i]=true; dfs(cur+1); ifVisited[i]=false;}}success:continue;}}int main(){ifstream file("1.csv");char temp;file>>startP>>temp>>endP>>temp;temp='|';mustNum=0;while(temp=='|'){mustNum++;file>>mustP[mustNum];temp='\n';file>>temp;}file.close();file.open("2.csv");lNum=pNum=0;int temp2;while(file>>temp2){lNum++;l[lNum].id=temp2;file>>temp>>l[lNum].start>>temp>>l[lNum].end>>temp>>l[lNum].length;if(pNum<l[lNum].start){pNum=l[lNum].start;}if(pNum<l[lNum].end){pNum=l[lNum].end;}temp2=-1001;}for(int i=1;i<=lNum;i++){ifVisitedLine[i]=false;}ifVisited=new bool[pNum+1];for(int i=1;i<=pNum;i++){ifVisited[i]=false;}ifVisited[startP]=true;plength=0;pathPNum=0;success=false;dfs(1);ofstream file2("3.csv");if(success==true){for(int i=pathPNum-1;i>=1;i--){file2<<l[successPath[i]].end;if(i!=1){file2<<"|";}}}else{file2<<"NA";}return 0;}
7 1
- 2016华为软件精英挑战赛初赛题目,个人分析与代码,尚未测试代码,因为没有judge系统啊!
- 2016华为精英软件挑战赛初赛思路及代码-基于模拟退火算法
- 华为软件精英挑战赛2016
- 2016华为软件精英挑战赛:初期算法设计方案及其代码实现
- 2017华为软件精英挑战赛思路分析
- 2017华为软件精英挑战赛解分析
- 海康威视2017软件精英挑战赛初赛题目
- 华为软件精英挑战赛2016题解
- 2016华为软件精英挑战赛总结
- 改进的蚁群算法Java——求解2016 code craft华为精英挑战赛初赛题目
- 华为软件精英挑战赛2015
- 2015华为软件精英挑战赛
- 2017 华为软件精英挑战赛
- 2017华为软件精英挑战赛
- 华为软件精英挑战赛总结
- 2017华为软件精英挑战赛
- 华为软件精英挑战赛总结
- 华为2017软件精英挑战赛赛题分析
- [POJ3422]Kaka's Matrix Travels 做题笔记
- 化繁为简的翻译机——解释器模式
- Cooike的基本认识
- 安卓开发——在Activity里如何获得另一个xml布局文件的控件
- linux scp远程拷贝文件及文件夹
- 2016华为软件精英挑战赛初赛题目,个人分析与代码,尚未测试代码,因为没有judge系统啊!
- 对象迁移表空间引出的三个小问题
- 学习python入门(一)
- 划分树 hdu2665 第k小
- PHP empty、isset、isnull的区别
- 基于webpack搭建前端工程解决方案探索
- IOS dispatch_once
- 【安卓基础四】adb命令使用Heap检测和分析Android应用内存
- Linux多线程及同步