POJ 3268 Silver Cow Party

奶牛派对:有分别来自 N 个农场的 N 头牛去农场 X 嗨皮,农场间由 M 条有向路径连接。每头牛来回都挑最短的路走,求它们走的路的最大长度?

们其实都是“图”

最短路 dijkstra 解决任意两点最短路的变种

用floyd的话会TLE,\(1000^3\)复杂度果然不是盖的,另外X的编号记得减一,测试用例很恶心的,即使忘了减一也照样得出正确答案10,但是一提交就\(WA\),让我深深地感到了来自命题者的恶意:

//第一次用OJ宏定义,提交的时候注释掉前3行即可
#ifndef ONLINE_JUDGE
#pragma warning(disalbe : 4996)
#endif
#include<iostream>
#include<algorithm>
#include<cstring>
using namespace std;
#define MAX_V 1024
int d[MAX_V][MAX_V];//d[u][v]表示边e=(u,v)的权值,不存在的时候等于无穷大或者d[i][i] = 0
int V;//顶点数 void floyd() {
for (int k = 0; k < V; ++k)
for (int i = 0; i < V; ++i)
for (int j = 0; j < V; ++j)
d[i][j] = min(d[i][j], d[i][k] + d[k][j]);
} ////////////////////////////////SubMain///////////////////////////////
int main() {
#ifndef ONLINE_JUDGE
freopen("in.txt", "r", stdin);
freopen("out.txt", "w", stdout);
#endif
int M, X;
cin >> V >> M >> X;
--X;
memset(d, 0x3f, V * MAX_V * sizeof(int));
for (int i = 0; i < V; ++i)d[i][i] = 0;
while (M--) {
int A, B, T;
cin >> A >> B >> T;
--A;
--B;
d[A][B] = T;
}
floyd();
int ans = 0;
for (int i = 0; i < V; ++i)
ans = max(ans, d[i][X] + d[X][i]);
cout << ans << endl;
#ifndef ONLINE_JUDGE
fclose(stdin);
fclose(stdout);
system("out.txt");
#endif // !ONLINE_JUDGE
return 0;
}
////////////////////////////////End Sub///////////////////////////////

dijkstra是解决单源最短路问题的,稍微修改一下就可以支持任意两点最短路:

//#ifndef ONLINE_JUDGE
//#pragma warning(disable : 4996)
//#endif
#include <iostream>
#include <algorithm>
#include <vector>
#include <queue>
#include <cstring>
#include <functional>
using namespace std;
#define MAX_V 1024 // 从顶点from指向顶点to的权值为cost的边
struct edge
{
int to, cost;
edge(){}
edge(int to, int cost) : to(to), cost(cost){}
}; // first 最短路径,second顶点编号
typedef pair<int, int> P; // 图
vector<edge> G[MAX_V]; // 最短距离
int d[MAX_V][MAX_V];
// V是顶点数,E是边数
int V, E; // 求解从顶点s出发到所有点的最短距离
void dijkstra(int s)
{
priority_queue<P, vector<P>, greater<P> > que;
memset(d[s], 0x3f, MAX_V * sizeof(int));
d[s][s] = 0;
que.push(P(0, s)); while (!que.empty())
{
P p = que.top(); que.pop();
int v = p.second;
if (d[s][v] < p.first) continue;
for (int i = 0; i < G[v].size(); ++i)
{
edge e = G[v][i];
if (d[s][e.to] > d[s][v] + e.cost)
{
d[s][e.to] = d[s][v] + e.cost;
que.push(P(d[s][e.to], e.to));
}
}
}
} ///////////////////////////SubMain//////////////////////////////////
int main(int argc, char *argv[])
{
#ifndef ONLINE_JUDGE
freopen("in.txt", "r", stdin);
freopen("out.txt", "w", stdout);
#endif
int M, X;
cin >> V >> M >> X;
--X;
while (M--)
{
int A, B, T;
cin >> A >> B >> T;
--A;
--B;
G[A].push_back(edge(B, T));
}
for (int i = 0; i < V; ++i)
{
dijkstra(i);
} int ans = 0;
for (int i = 0; i < V; ++i)
{
if (i == X)
{
continue;
}
ans = max(ans, d[i][X] + d[X][i]);
} cout << ans << endl;
#ifndef ONLINE_JUDGE
fclose(stdin);
fclose(stdout);
system("out.txt");
#endif
return 0;
}
///////////////////////////End Sub//////////////////////////////////
Time 719ms
Memory 4736kB
Length 1651
Lang G++
Submitted 2020-05-14 11:15:13

不过上面那个实在太浪费,我只想计算起点或终点是X的路径最短路问题,可以在上面while (!que.empty())的循环里加入判断条件,还可以这么玩:

来一个反向图,交换边的起点和终点得到反向的有向图,两次dijkstra解决问题:

//#ifndef ONLINE_JUDGE
//#pragma warning(disable :4996)
//#endif // !ONLINE_JUDGE
#include <iostream>
#include <algorithm>
#include <vector>
#include <queue>
#include<cstring>
#include <functional>
using namespace std;
#define MAX_V 10240 // 从顶点from指向顶点to的权值为cost的边
struct edge
{
int to, cost;
edge() {}
edge(int to, int cost) : to(to), cost(cost) {}
}; // first 最短路径,second顶点编号
typedef pair<int, int> P; // 图
vector<vector<edge> > G(MAX_V);
// 反向图
vector<vector<edge> > RG(MAX_V); // 最短距离
int d[MAX_V];
int rd[MAX_V];
// V是顶点数,E是边数
int V, E; // 求解从顶点s出发到所有点的最短距离
void dijkstra(int s)
{
priority_queue<P, vector<P>, greater<P> > que;
memset(d, 0x3f, sizeof(d));
d[s] = 0;
que.push(P(0, s)); while (!que.empty())
{
P p = que.top(); que.pop();
int v = p.second;
if (d[v] < p.first) continue;
for (int i = 0; i < G[v].size(); ++i)
{
edge e = G[v][i];
if (d[e.to] > d[v] + e.cost)
{
d[e.to] = d[v] + e.cost;
que.push(P(d[e.to], e.to));
}
}
}
} ///////////////////////////SubMain//////////////////////////////////
int main()
{
#ifndef ONLINE_JUDGE
freopen("in.txt", "r", stdin);
freopen("out.txt", "w", stdout);
#endif
int M, X;
cin >> V >> M >> X;
--X;
while (M--)
{
int A, B, T;
cin >> A >> B >> T;
--A;
--B;
G[A].push_back(edge(B, T));
RG[B].push_back(edge(A, T));
}
dijkstra(X);
G = RG;
memcpy(rd, d, sizeof(d));
dijkstra(X);
for (int i = 0; i < V; ++i)
{
d[i] += rd[i];
} cout << *max_element(d, d + V) << endl;
#ifndef ONLINE_JUDGE
fclose(stdin);
fclose(stdout);
system("out.txt");
#endif
return 0;
}
///////////////////////////End Sub//////////////////////////////////

优化以后Time降到了 235ms

POJ 3268 Silver Cow Party 题解 《挑战程序设计竞赛》的更多相关文章

  1. POJ 3268 Silver Cow Party (最短路径)

    POJ 3268 Silver Cow Party (最短路径) Description One cow from each of N farms (1 ≤ N ≤ 1000) convenientl ...

  2. POJ 3268 Silver Cow Party 最短路—dijkstra算法的优化。

    POJ 3268 Silver Cow Party Description One cow from each of N farms (1 ≤ N ≤ 1000) conveniently numbe ...

  3. POJ 3268 Silver Cow Party 最短路

    原题链接:http://poj.org/problem?id=3268 Silver Cow Party Time Limit: 2000MS   Memory Limit: 65536K Total ...

  4. POJ 3268 Silver Cow Party (双向dijkstra)

    题目链接:http://poj.org/problem?id=3268 Silver Cow Party Time Limit: 2000MS   Memory Limit: 65536K Total ...

  5. POJ 3268——Silver Cow Party——————【最短路、Dijkstra、反向建图】

    Silver Cow Party Time Limit:2000MS     Memory Limit:65536KB     64bit IO Format:%I64d & %I64u Su ...

  6. POJ 3268 Silver Cow Party (最短路dijkstra)

    Silver Cow Party 题目链接: http://acm.hust.edu.cn/vjudge/contest/122685#problem/D Description One cow fr ...

  7. poj 3268 Silver Cow Party(最短路)

    Silver Cow Party Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 17017   Accepted: 7767 ...

  8. POJ 3268 Silver Cow Party 最短路径+矩阵转换

    Silver Cow Party Time Limit : 4000/2000ms (Java/Other)   Memory Limit : 131072/65536K (Java/Other) T ...

  9. 图论 ---- spfa + 链式向前星 ---- poj 3268 : Silver Cow Party

    Silver Cow Party Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 12674   Accepted: 5651 ...

  10. DIjkstra(反向边) POJ 3268 Silver Cow Party || POJ 1511 Invitation Cards

    题目传送门 1 2 题意:有向图,所有点先走到x点,在从x点返回,问其中最大的某点最短路程 分析:对图正反都跑一次最短路,开两个数组记录x到其余点的距离,这样就能求出来的最短路以及回去的最短路. PO ...

随机推荐

  1. [Codechef REBXOR]Nikitosh and xor (Trie,异或)

    题目传送门 分析:首次考虑暴力枚举 \(l_{1},r_{1},l_{2},r_{2}\),配合前缀和时间复杂度 \(O(N^{4})\),需要想办法优化.对于这种两段区间不重合的,我们考虑枚举两段区 ...

  2. DevOps|研发提效-敏捷开发之每日站立会

    对于研发效能团队建设和组织,本文不再赘述,可以参考之前的文章,已经讲得很透彻了.本文重点讲我们日常是怎么开站立会,怎么让团队跑起来,高效能产出的.每日站立会,15分钟到30分钟,看似非常短的一个会,但 ...

  3. Nim 枚举类型 对性能的影响

    Nim 枚举类型 对性能的影响 继上一篇文章<Nim 概念 Concept 对性能的影响>后,我在想,既然 method 虚方法造成性能的影响很大,那么有没有更快的方法实现,当然是有的,那 ...

  4. Salesforce LWC学习(四十六) 自定义Datatable实现cell onclick功能

    本篇参考:https://developer.salesforce.com/docs/component-library/bundle/lightning-datatable 背景:我们有时会有这种类 ...

  5. Java中的try-catch

    try里面放入可以尝试的操作,而catch则是接受try里面的异常,从而进行的操作,其目的是为了不让程序因为异常而中断,具体的流程是 抛出异常是可以自己设置,这里是自己设置的异常类fg,catch括号 ...

  6. 记录一个MySQL中order by 和 limit 连用导致分页查询不生效的坑

    具体现象和这位同学的一致,具体的解决办法也是参考这位同学的做法 参考文章地址:https://www.cnblogs.com/yuluoxingkong/p/10681583.html

  7. 三种方式查询三级分类Tree

    话不多说,直接上代码 方式一:for循环嵌套一下 /** * 查询三级分类 * * @return */ @Override public List<GoodsType> findNode ...

  8. vivo 容器平台资源运营实践

    作者:vivo 互联网服务器团队 - Chen Han 容器平台针对业务资源申请值偏大的运营问题,通过静态超卖和动态超卖两种技术方案,使业务资源申请值趋于合理化,提高平台资源装箱率和资源利用率. 一. ...

  9. RV1126 分区教程

    一.前言 期初我是想弄一个分区存放自己的 APP 程序,如果需要更改应用的时候,只需要烧写独立的分区即可,就不需要重新烧写 rootfs.这是一个简单的操作,为啥还需要记录了,因为我在里面遇到了一些坑 ...

  10. CVE-2016-5734 复现

    CVE-2016-5734 漏洞简介 phpMyAdmin 4.0.x-4.6.2 远程代码执行漏洞(CVE-2016-5734) phpMyAdmin是一套开源的.基于Web的MySQL数据库管理工 ...