NSOJ 鬼泣

今天组队赛的一道最短路的题,给你一个矩阵,矩阵上有L,R,G,A,分别表示当你到达这个点的时候你要向左,向右,向前,向后走,如果要向别的方向走需要花费1点的魔力,正常情况下走需要花费1点的时间。问花费最小魔力的时候的最少时间是多少。 一个机智的处理方法是向别的方向走的时候的花费1*100000000,然后构图跑最短路出来的结果/100000000就是最小的魔力,%100000000就是最小的时间。

但是比赛的时候WA了好久,赛后RE了好久。终于发现一个严重的问题----队列开小了。

平时最短路都是STL里的队列,这次用了手写的队列,然后手写的队列又没有弄成循环的队列,所以就跪了。写下来警醒自己:

手写队列要小心!!!!!

手写队列要小心!!!!!

手写队列要小心!!!!!

#pragma warning(disable:4996)
#include <iostream>
#include <cstring>
#include <string>
#include <vector>
#include <cstdio>
#include <algorithm>
#include <cmath>
#include <queue>
#include <map>
#include <ctime>
using namespace std;

#define maxn 120
#define ll long long
int n, m;

int dx[4] = { 0, 1, 0, -1 };
int dy[4] = { 1, 0, -1, 0 };

const ll hcost = 100000000;

int cd(int k, char cmd){
	if (cmd == ‘G‘) return k;
	else if (cmd == ‘L‘) return (k + 3) % 4;
	else if (cmd == ‘R‘) return (k + 1) % 4;
	else return (k + 2) % 4;
}

char b[maxn][maxn];

struct Edge{
	int v; ll w;
	Edge(int vi, ll wi) :v(vi), w(wi){}
	Edge(){}
};
vector<Edge> G[maxn*maxn * 8];

int getid(int i, int j, int k){
	return 4 * (i*m + j) + k;
}

bool in[maxn*maxn * 8];
ll d[maxn*maxn * 8];
bool vis[maxn*maxn * 8];

void spfa()
{
	memset(in, 0, sizeof(in));
	memset(d, 0x3f, sizeof(d));
	memset(vis, 0, sizeof(vis));
	in[0] = true; d[0] = 0;
	queue<int> que;
	que.push(0);
	while (!que.empty()){
		int u = que.front(); in[u] = false; que.pop();
		for (int i = 0; i < G[u].size(); ++i){
			int v = G[u][i].v;
			ll w = G[u][i].w;
			if (d[u] + w < d[v]){
				d[v] = d[u] + w;
				if (!in[v]) {
					que.push(v);
					in[v] = true;
				}
			}
		}
	}
}

int main()
{
	//freopen("C.in", "r", stdin);
	//freopen("out.txt", "w", stdout);
	//double t1 = clock();
	while (cin >> n >> m){
		for (int i = 0; i < n; ++i){
			scanf("%s", b[i]);
		}
		for (int i = 0; i <= n*m * 6; ++i){
			G[i].clear();
		}
		for (int i = 0; i < n; ++i){
			for (int j = 0; j < m; ++j){
				for (int k = 0; k < 4; ++k){
					int id = getid(i, j, k);
					char cmd = b[i][j];
					int cord = cd(k, cmd);
					int xx, yy;
					for (int kk = 0; kk < 4; ++kk){
						xx = i + dx[kk]; yy = j + dy[kk];
						if (!(xx >= 0 && xx < n&&yy >= 0 && yy < m)) continue;
						if (kk == cord) {
							G[id].push_back(Edge(getid(xx, yy, kk), 1LL));
						}
						else{
							G[id].push_back(Edge(getid(xx, yy, kk), hcost + 1));
						}
					}
				}
			}
		}
		spfa();
		ll ans = 1e15;
		for (int i = 0; i < 4; ++i){
			int idd = getid(n - 1, m - 1, i);
			ans = min(ans, d[idd]);
		}
		printf("%lld %lld\n", ans / hcost, ans%hcost);
	}
	//double t2 = clock();
	//cout << t2 - t1 << endl;
	return 0;
}

NSOJ 鬼泣,布布扣,bubuko.com

时间: 2024-10-14 00:15:20

NSOJ 鬼泣的相关文章

【游戏】【鬼泣4】边玩边记(一)

前面忘了记了,大火牛打啊打啊就过了,貌似揍脑袋好一些.大蛤蟆吃了不少亏,后来在论坛里才看到站在身侧就安全了,自己当时过于一根筋了,被吃了好多次.下面是最新进展啦~1.怎么对付幽灵幽灵披着破麻袋一样的衣服,在天上飞啊飞,攻击手段是吐出一根触角扎你.一直跳着砍,或者等它靠近地面后上去砍,结果收效甚微,还差点被扎死.偶然发现了攻击的要点,只需要找到幽灵的位置,跳起,跳到幽灵身边后,按L键就可以抓住它扔到地上,这样幽灵就变成龙虾一样的骨头架子了,上去干掉就可以啦~~2.管道里的鲨鱼就是管道里有三个鲨鱼鳍

【游戏】鬼泣4真的很华丽啊~~

昨晚又玩了一会儿鬼泣4,打了两关.在最低难度下,真的很惬意,BOSS战也不是很难(昨晚揍的是那个大蛤蟆).可惜一直没抓住击杀要点,最后一下是迷迷糊糊的抓住了蛤蟆的尾巴,把它给干掉了,其间吃了两个小血一个大血,最终的过关评价是“C”,哈哈,我果然对于动作类游戏不在行~~不过我要求不高,能过了就行,欣赏画面是第一位的,吼吼~~值得一说的是,有一个隐藏关,就是要求人不落地,做5次空中抓投.看似很难,其实抓住要点就不难啦.第一次尝试,手忙脚乱,右手不停的在那按按按,结果怪死绝了也没能达到5次空投.第二次

【游戏】【鬼泣4】边玩边记(二)

鬼泣真的超好玩啊~~1.需要让攻击达到一定评价才能打开的雕像这个打得真的很累,一直按到手抽筋.最困难的是,同样的招数还不能总用,因为使用同样的招数不仅不会继续提升评价,相反的,还会降低评价,忙得我上下翻飞,很勉强的才打开了这个雕像,获得那个小蓝石.2.骑士队长(天使形的BOSS)刚开始完全没有还手之力,无论我出什么招式都会很轻松的把我打倒.后来发现了小窍门,我只要走过去骗他的攻击,躲开他的攻击后,他会有很长时间的僵直,我就可以轻松的切他啦,按L键后的投技特效真的很爽啊~~3.绞肉机一样的电梯需要

鬼泣之家用数据中心

鬼泣之家用数据中心 VSAN(存储)+NSX(网络)+horizon(应用)+vrealize(监控)+veeam(备份)+ossim(侦听)+prtg(运维) 假设你家有一间客厅一间卧室,客厅和卧室都有一个小格子,客厅的格子里面你可以放cisco asa5506X+cisco 2960X,三台沙漠之鹰二(mini-itx,内置c236芯片组,i5,ddr4,ssd+hhd,双网卡), 而卧室也有一个小格子,里面放juniper srx 210he ,juniperex3200,三台沙漠之鹰二.

最近想写一个类似鬼泣 收集红魂的功能,陆续写点东西作为笔记

OnComponentBeginOverlap事件 当物体有碰撞体,同事碰撞类型设置为OverlapAll时,会触发,同时角色不会被挡住. 这是文档中的OnComponentBeginOverlap的案例代码 // set up a notification for when this component overlaps something CollisionSphere->OnComponentBeginOverlap.AddDynamic(this, &ALightSwitchCode

【游戏】【鬼泣4】边玩边记(三)

终于通关了.1.有迷雾的迷宫那一关.迷路了,本来来到了正确的路,却忘了怎么走.关键词:跳桥.桥下.楼梯下.上山.2.最后任务的老头子真的没想到这么好杀,直接轰至渣.最后那个大石头人,摸索了很久才明白,第一拳落下,需要躲闪开,然后对着拳头用L键,第二拳,在拳头打来时对着拳头按L键,然后它就屈服了.3.女主角这身材……这相貌……唉…… (此篇博客搬迁于百度空间,原发布日期为:2009-09-07)

NSOJ Constructing Roads(图论)

There are N villages, which are numbered from 1 to N, and you should build some roads such that every two villages can connect to each other. We say two village A and B are connected, if and only if there is a road between A and B, or there exists a

鬼泣模仿秀&lt;01&gt;——Unity3D实现类似鬼泣的蓄力攻击(C#)

1 float KeyTime=0f; 2 bool addTime=false; 3 void Update () { 4 if (Input.GetKeyDown (KeyCode.J)) { 5 addTime=true; 6 //播放蓄力动画 7 } 8 if (Input.GetKeyUp (KeyCode.J)) { 9 addTime=false; 10 Choose (KeyTime); 11 KeyTime=0f; 12 } 13 if (addTime) { 14 KeyTi

NSOJ 畅通工程()

某省调查城镇交通状况,得到现有城镇道路统计表,表中列出了每条道路直接连通的城镇.省政府“畅通工程”的目标是使全省任何两个城镇间都可以实现交通(但不一定有直接的道路相连,只要互相间接通过道路可达即可).问最少还需要建设多少条道路? Input 测试输入包含若干测试用例.每个测试用例的第1行给出两个正整数,分别是城镇数目N ( < 1000 )和道路数目M:随后的M行对应M条道路,每行给出一对正整数,分别是该条道路直接连通的两个城镇的编号.为简单起见,城镇从1到N编号. 注意:两个城市之间可以有多条