P2910 [USACO08OPEN] Clear And Present Danger S

39 阅读1分钟

P2910 [USACO08OPEN] Clear And Present Danger S

这题是一道多源最短路的问题,所以可以使用floyd算法。

#pragma GCC optimize(1)

#pragma GCC optimize(2)

#pragma GCC optimize(3)

#pragma GCC optimize("Os")

#pragma GCC optimize("Ofast")

#pragma GCC optimize("Og")

#pragma GCC optimize("inline")

#include<bits/stdc++.h>

using namespace std;

typedef long long ll;

typedef unsigned long long ull;

typedef pair <ll , ll> pii;

typedef priority_queue <ll ,vector ,greater > xiao;

typedef priority_queue <ll ,vector ,less > da;

const int N=1e5 + 10,M = 0x3f3f3f3f;

const ull P = 131;

int n,m;

int res[N];

int g[105][105];

void floyd() {

for(int k = 1 ; k <= n ; k++)
{
	for(int i = 1 ; i <= n ; i++)
	{
		for(int j = 1 ; j <= n ; j++)
		{
			g[i][j] = min(g[i][j] , g[k][j] + g[i][k]);
		}
	}
}

}

int main()

{

std::ios::sync_with_stdio(false);
std::cin.tie(0),cout.tie(0);

cin>>n>>m;

for(int i = 1 ; i <= m ; i++)
{
	cin>>res[i];
}

for(int i = 1 ; i <= n ; i++)
{
	for(int k = 1 ; k <= n ; k++)
	{
		if(i == k)
		{
			g[i][k] = 0;
		}else
		{
			g[i][k] = M;
		}
	}
}

for(int i = 1 ; i <= n ; i++)
{
	for(int k = 1 ; k <= n ; k++)
	{
		int num;
		cin>>num;
		g[i][k] = min(g[i][k] , num);
	}
}

floyd();
ll ans = 0;
res[0] = 1;


for(int i = 1 ; i <= m ; i++)
{

	ans += g[res[i - 1]][res[i]];
}

cout<<ans;

}