由于每个点的状态包含走过来的距离,所以要存二维的状态,但是状态总量太多,所以可以用哈希来搞。

那么就是bfs最短路,哈希记录状态了。

#include <iostream>
#include <cstdio>
#include <cstring>
using namespace std;
const int maxn=5e3+9;
int n,m;
int a[maxn];
struct
{
struct
{
int next,to;
}e[maxn*10];
int head[maxn],lon;
void clear()
{
memset(head,-1,sizeof(head));
lon=-1;
}
void add(int from,int to)
{
e[++lon].to=to;
e[lon].next=head[from];
head[from]=lon;
}
}edge; struct
{
int head[111111],lon;
struct
{
int t,dist,next,sum;
}data[1111111];
void clear()
{
memset(head,-1,sizeof(head));
lon=-1;
}
bool push(int t,int dist,int sum)
{
int key=(t+abs(dist)%360*n)%111111;
for(int k=head[key];k!=-1;k=data[k].next)
{
if(t==data[k].t&&dist==data[k].dist)
return false;
}
data[++lon].t=t;
data[lon].dist=dist;
data[lon].next=head[key];
data[lon].sum=sum;
head[key]=lon;
return true;
}
}hash; struct
{
int t,dist,sum;
}que[1111111];
int bfs()
{
hash.clear();
int front=1,end=0;
que[++end].t=1;
que[end].sum=que[end].dist=0;
hash.push(1,0,0); while(front<=end)
{
int t=que[front].t;
int dist=que[front].dist;
int sum=que[front++].sum;
for(int k=edge.head[t];k!=-1;k=edge.e[k].next)
{
int u=edge.e[k].to;
int c=(a[u]+360-a[t])%360;
int uc=(a[t]+360-a[u])%360;
int tmp;
if(c<uc) tmp=c;
else tmp=-uc;
if(u==1&&dist+tmp!=0) return sum+1;
if(hash.push(u,dist+tmp,sum+1))
{
que[++end].t=u;
que[end].dist=dist+tmp;
que[end].sum=sum+1;
}
}
}
return -1;
} int main()
{
// freopen("in.txt","r",stdin);
while(scanf("%d %d",&n,&m)!=EOF)
{
edge.clear();
for(int i=1;i<=n;i++)
scanf("%d",&a[i]);
for(int i=1,from,to;i<=m;i++)
{
scanf("%d %d",&from,&to);
edge.add(from,to);
edge.add(to,from);
}
cout<<bfs()<<endl;
}
return 0;
}
#include <iostream>
#include <cstdio>
#include <cstring>
using namespace std;
const int maxn=5e3+9;
int n,m;
int a[maxn];
struct
{
struct
{
int next,to;
}e[maxn*10];
int head[maxn],lon;
void clear()
{
memset(head,-1,sizeof(head));
lon=-1;
}
void add(int from,int to)
{
e[++lon].to=to;
e[lon].next=head[from];
head[from]=lon;
}
}edge; struct
{
int head[111111],lon;
struct
{
int t,dist,next,sum;
}data[1111111];
void clear()
{
memset(head,-1,sizeof(head));
lon=-1;
}
bool push(int t,int dist,int sum)
{
int key=(t+abs(dist)%360*n)%111111;
for(int k=head[key];k!=-1;k=data[k].next)
{
if(t==data[k].t&&dist==data[k].dist)
return false;
}
data[++lon].t=t;
data[lon].dist=dist;
data[lon].next=head[key];
data[lon].sum=sum;
head[key]=lon;
return true;
}
}hash; struct
{
int t,dist,sum;
}que[1111111];
int bfs()
{
hash.clear();
int front=1,end=0;
que[++end].t=1;
que[end].sum=que[end].dist=0;
hash.push(1,0,0); while(front<=end)
{
int t=que[front].t;
int dist=que[front].dist;
int sum=que[front++].sum;
for(int k=edge.head[t];k!=-1;k=edge.e[k].next)
{
int u=edge.e[k].to;
int c=(a[u]+360-a[t])%360;
int uc=(a[t]+360-a[u])%360;
int tmp;
if(c<uc) tmp=c;
else tmp=-uc;
if(u==1&&dist+tmp!=0) return sum+1;
if(hash.push(u,dist+tmp,sum+1))
{
que[++end].t=u;
que[end].dist=dist+tmp;
que[end].sum=sum+1;
}
}
}
return -1;
} int main()
{
// freopen("in.txt","r",stdin);
while(scanf("%d %d",&n,&m)!=EOF)
{
edge.clear();
for(int i=1;i<=n;i++)
scanf("%d",&a[i]);
for(int i=1,from,to;i<=m;i++)
{
scanf("%d %d",&from,&to);
edge.add(from,to);
edge.add(to,from);
}
cout<<bfs()<<endl;
}
return 0;
}
#include
#include <iostream>
#include <cstdio>
#include <cstring>
using namespace std;
const int maxn=5e3+9;
int n,m;
int a[maxn];
struct
{
struct
{
int next,to;
}e[maxn*10];
int head[maxn],lon;
void clear()
{
memset(head,-1,sizeof(head));
lon=-1;
}
void add(int from,int to)
{
e[++lon].to=to;
e[lon].next=head[from];
head[from]=lon;
}
}edge; struct
{
int head[111111],lon;
struct
{
int t,dist,next,sum;
}data[1111111];
void clear()
{
memset(head,-1,sizeof(head));
lon=-1;
}
bool push(int t,int dist,int sum)
{
int key=(t+abs(dist)%360*n)%111111;
for(int k=head[key];k!=-1;k=data[k].next)
{
if(t==data[k].t&&dist==data[k].dist)
return false;
}
data[++lon].t=t;
data[lon].dist=dist;
data[lon].next=head[key];
data[lon].sum=sum;
head[key]=lon;
return true;
}
}hash; struct
{
int t,dist,sum;
}que[1111111];
int bfs()
{
hash.clear();
int front=1,end=0;
que[++end].t=1;
que[end].sum=que[end].dist=0;
hash.push(1,0,0); while(front<=end)
{
int t=que[front].t;
int dist=que[front].dist;
int sum=que[front++].sum;
for(int k=edge.head[t];k!=-1;k=edge.e[k].next)
{
int u=edge.e[k].to;
int c=(a[u]+360-a[t])%360;
int uc=(a[t]+360-a[u])%360;
int tmp;
if(c<uc) tmp=c;
else tmp=-uc;
if(u==1&&dist+tmp!=0) return sum+1;
if(hash.push(u,dist+tmp,sum+1))
{
que[++end].t=u;
que[end].dist=dist+tmp;
que[end].sum=sum+1;
}
}
}
return -1;
} int main()
{
// freopen("in.txt","r",stdin);
while(scanf("%d %d",&n,&m)!=EOF)
{
edge.clear();
for(int i=1;i<=n;i++)
scanf("%d",&a[i]);
for(int i=1,from,to;i<=m;i++)
{
scanf("%d %d",&from,&to);
edge.add(from,to);
edge.add(to,from);
}
cout<<bfs()<<endl;
}
return 0;
}
<iostream>#include <cstdio>#include <cstring>using namespace std;const int maxn=5e3+9;int n,m;int a[maxn];struct{    struct    {        int next,to;    }e[maxn*10];    int head[maxn],lon;    void clear()    {        memset(head,-1,sizeof(head));        lon=-1;    }    void add(int from,int to)    {        e[++lon].to=to;        e[lon].next=head[from];        head[from]=lon;    }}edge;struct{    int head[1111111],lon;    struct    {        int t,dist,next,sum;    }data[1111111];    void clear()    {        memset(head,-1,sizeof(head));        lon=-1;    }    bool push(int t,int dist,int sum)    {        int key=t+abs(dist)%360*n;        for(int k=head[key];k!=-1;k=data[k].next)        {            if(t==data[k].t&&dist==data[k].dist)            return false;        }        data[++lon].t=t;        data[lon].dist=dist;        data[lon].next=head[key];        data[lon].sum=sum;        head[key]=lon;        return true;    }}hash;struct{    int t,dist,sum;}que[1111111];int bfs(){    hash.clear();    int front=1,end=0;    que[++end].t=1;    que[end].sum=que[end].dist=0;    hash.push(1,0,0);    while(front<=end)    {        int t=que[front].t;        int dist=que[front].dist;        int sum=que[front++].sum;        for(int k=edge.head[t];k!=-1;k=edge.e[k].next)        {            int u=edge.e[k].to;            int c=(a[u]+360-a[t])%360;            int uc=(a[t]+360-a[u])%360;            int tmp;            if(c<uc) tmp=c;            else tmp=-uc;            if(u==1&&dist+tmp!=0) return sum+1;            if(hash.push(u,dist+tmp,sum+1))            {                que[++end].t=u;                que[end].dist=dist+tmp;                que[end].sum=sum+1;            }        }    }    return -1;}int main(){//    freopen("in.txt","r",stdin);    while(scanf("%d %d",&n,&m)!=EOF)    {        edge.clear();        for(int i=1;i<=n;i++)        scanf("%d",&a[i]);        for(int i=1,from,to;i<=m;i++)        {            scanf("%d %d",&from,&to);            edge.add(from,to);            edge.add(to,from);        }        cout<<bfs()<<endl;    }    return 0;}

poj 2432 Around the world bfs+哈希的更多相关文章

  1. POJ 2432

    \(\mathbf{POJ\;2432}\)题解 题意 给出圆上的\(N\)个点,每个点有一个经度(大于\(0\)小于\(360\)):再给出\(M\)条双向边,保证边\(x y\)仅会沿圆上较短的弧 ...

  2. POJ 2251 Dungeon Master --- 三维BFS(用BFS求最短路)

    POJ 2251 题目大意: 给出一三维空间的地牢,要求求出由字符'S'到字符'E'的最短路径,移动方向可以是上,下,左,右,前,后,六个方向,每移动一次就耗费一分钟,要求输出最快的走出时间.不同L层 ...

  3. POJ 1426 Find The Multiple --- BFS || DFS

    POJ 1426 Find The Multiple 题意:给定一个整数n,求n的一个倍数,要求这个倍数只含0和1 参考博客:点我 解法一:普通的BFS(用G++能过但C++会超时) 从小到大搜索直至 ...

  4. UVA 10651 Pebble Solitaire(bfs + 哈希判重(记忆化搜索?))

    Problem A Pebble Solitaire Input: standard input Output: standard output Time Limit: 1 second Pebble ...

  5. POJ.3894 迷宫问题 (BFS+记录路径)

    POJ.3894 迷宫问题 (BFS+记录路径) 题意分析 定义一个二维数组: int maze[5][5] = { 0, 1, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, ...

  6. POJ 3669 Meteor Shower【BFS】

    POJ 3669 去看流星雨,不料流星掉下来会砸毁上下左右中五个点.每个流星掉下的位置和时间都不同,求能否活命,如果能活命,最短的逃跑时间是多少? 思路:对流星雨排序,然后将地图的每个点的值设为该点最 ...

  7. POJ 1573 Robot Motion(BFS)

    Robot Motion Time Limit: 1000MS   Memory Limit: 10000K Total Submissions: 12856   Accepted: 6240 Des ...

  8. [POJ 1635] Subway tree systems (树哈希)

    题目链接:http://poj.org/problem?id=1635 题目大意:给你两棵树的dfs描述串,从根节点出发,0代表向深搜,1代表回溯. 我刚开始自己设计了哈希函数,不知道为什么有问题.. ...

  9. POJ 3126 Prime Path (BFS)

    [题目链接]click here~~ [题目大意]给你n,m各自是素数,求由n到m变化的步骤数,规定每一步仅仅能改变个十百千一位的数,且变化得到的每个数也为素数 [解题思路]和poj 3278类似.b ...

随机推荐

  1. hdu5294||2015多校联合第一场1007 最短路+最大流

    http://acm.hdu.edu.cn/showproblem.php? pid=5294 Problem Description Innocent Wu follows Dumb Zhang i ...

  2. TCP SOCKET中backlog参数的用途是什么? ---图解

    recv_queue中的包大小,为内核的包大小,而不是ip包大小. 如果发出去的包太大,需要修改write_queue和tx_queue两个参数,tx_queue主要是流量控制. 多进程必须在sock ...

  3. QTableWidget的使用和美工总结

    基本外观设置 FriendTable->setFrameShape(QFrame::NoFrame);  //设置边框 FriendTable->setHorizontalHeaderLa ...

  4. AndroidStudio工程文件导入Jar包和So第三方库

    AndroidStudio 导入Jar包和第三方So库 在android开发中,需要导入许多第三方的jar包和so库来支持,包括像许多第三方的支持平台--友盟,环信.融云.极光推送.微博.腾讯等第三方 ...

  5. WPF TextSelection获取选中部分内容

    一.简单实例 //TextSelect继承自TextRange TextSelection selection = richTextBox.Selection; //1.获取选中内容 string r ...

  6. vs2013下的WCFRest 模板开发WCF

    在vs2013下使用wcfRestservice40 是安装不成功的,尝试多遍,都是这样.查看以前vs2012做的wcfrest,经过调教,终于在vs2013下也可以了! 1.新建wcf服务应用程序 ...

  7. Android 控件 之 Menu 菜单

    http://www.cnblogs.com/Mrs-cc/archive/2012/07/21/2603042.html 1.OptionsMenu (选项菜单)用法总结   使用方法: 方法一:添 ...

  8. C#中的Dictionary字典类介绍

      Dictionary字典类介绍 必须包含名空间System.Collection.Generic    Dictionary里面的每一个元素都是一个键值对(由二个元素组成:键和值)    键必须是 ...

  9. CGContextRef一点用法

      quartz 是主要的描画接口,支持基于路径的描画.抗锯齿渲染.渐变填充模式.图像.颜色.坐标空间变换.以及PDF 文档的创建.显示.和分析.UIKit 为Quartz 的图像和颜色操作提供了Ob ...

  10. java基础之抽象类与接口的区别

    在学习java的过程中,或者是在找工作笔试或面试的时候,如果你是java岗位,那么抽象类与接口的区别无疑是一个大热点,是各大公司都想要考的一个小知识点,下面是我为了9月份秋招自己总结的,若有不对的地方 ...