D. Fair
time limit per test

2 seconds

memory limit per test

512 megabytes

input

standard input

output

standard output

Some company is going to hold a fair in Byteland. There are $$$n$$$ towns in Byteland and $$$m$$$ two-way roads between towns. Of course, you can reach any town from any other town using roads.

There are $$$k$$$ types of goods produced in Byteland and every town produces only one type. To hold a fair you have to bring at least $$$s$$$ different types of goods. It costs $$$d(u,v)$$$ coins to bring goods from town $$$u$$$ to town $$$v$$$ where $$$d(u,v)$$$ is the length of the shortest path from $$$u$$$ to $$$v$$$. Length of a path is the number of roads in this path.

The organizers will cover all travel expenses but they can choose the towns to bring goods from. Now they want to calculate minimum expenses to hold a fair in each of $$$n$$$ towns.

Input

There are $$$4$$$ integers $$$n$$$, $$$m$$$, $$$k$$$, $$$s$$$ in the first line of input ($$$1 \le n \le 10^{5}$$$, $$$0 \le m \le 10^{5}$$$, $$$1 \le s \le k \le min(n, 100)$$$) — the number of towns, the number of roads, the number of different types of goods, the number of different types of goods necessary to hold a fair.

In the next line there are $$$n$$$ integers $$$a_1, a_2, \ldots, a_n$$$ ($$$1 \le a_{i} \le k$$$), where $$$a_i$$$ is the type of goods produced in the $$$i$$$-th town. It is guaranteed that all integers between $$$1$$$ and $$$k$$$ occur at least once among integers $$$a_{i}$$$.

In the next $$$m$$$ lines roads are described. Each road is described by two integers $$$u$$$ $$$v$$$ ($$$1 \le u, v \le n$$$, $$$u \ne v$$$) — the towns connected by this road. It is guaranteed that there is no more than one road between every two towns. It is guaranteed that you can go from any town to any other town via roads.

Output

Print $$$n$$$ numbers, the $$$i$$$-th of them is the minimum number of coins you need to spend on travel expenses to hold a fair in town $$$i$$$. Separate numbers with spaces.

Examples
Input
5 5 4 3
1 2 4 3 2
1 2
2 3
3 4
4 1
4 5
Output
2 2 2 2 3 
Input
7 6 3 2
1 2 3 3 2 2 1
1 2
2 3
3 4
2 5
5 6
6 7
Output
1 1 1 2 2 1 1 
Note

Let's look at the first sample.

To hold a fair in town $$$1$$$ you can bring goods from towns $$$1$$$ ($$$0$$$ coins), $$$2$$$ ($$$1$$$ coin) and $$$4$$$ ($$$1$$$ coin). Total numbers of coins is $$$2$$$.

Town $$$2$$$: Goods from towns $$$2$$$ ($$$0$$$), $$$1$$$ ($$$1$$$), $$$3$$$ ($$$1$$$). Sum equals $$$2$$$.

Town $$$3$$$: Goods from towns $$$3$$$ ($$$0$$$), $$$2$$$ ($$$1$$$), $$$4$$$ ($$$1$$$). Sum equals $$$2$$$.

Town $$$4$$$: Goods from towns $$$4$$$ ($$$0$$$), $$$1$$$ ($$$1$$$), $$$5$$$ ($$$1$$$). Sum equals $$$2$$$.

Town $$$5$$$: Goods from towns $$$5$$$ ($$$0$$$), $$$4$$$ ($$$1$$$), $$$3$$$ ($$$2$$$). Sum equals $$$3$$$.

【题意】

$$$n$$$个结点,$$$m$$$条边,$$$s$$$种商品,每个结点含有一种商品,且保证所有商品至少被一个结点包含。对于每个结点,选择至少$$$k$$$个结点,使他们包含至少$$$k$$$种商品,且到该结点的总距离和最小。

【思路】

结点和边的数量为1e5,而商品个数只有100,如果从每个结点出发直到寻找$$$k$$$个商品为止,那么这样做其实并不划算,其原因在于很难决定最近的商品在哪条路上,需要搜索到很深的地方,而且含有相同商品的城市会被反复访问。为了节约时间,可以预先从商品出发进行bfs,那么经过的城市都是最近的,这样处理以后每个城市就知道,自己到每个商品的最近距离,要凑齐$$$k$$$个商品只需要选择前k个最小的距离就行了。

【注意】

这里的bfs需要抽象理解一下,假如对$$$i$$$号商品进行bfs,那么第一步就要直接转移到所有含$$$i$$$的城市,然后就是平常的bfs了,每次扩展1个距离,遍历完所有城市后,每个城市就都有一个获得$$$i$$$的最短距离了。

【代码】

 #include<stdio.h>
#include<queue>
#include<memory.h>
#include<algorithm>
#include<vector> using std::queue;
using std::vector;
using std::sort; vector<int> t[];
#define N 100005
vector<int>node[N];
int cost[N][] = { };
int vis[N];
void bfs(int si) {
queue<int>help; int sz = t[si].size();
//将含si的所有城市加入到bfs的第一次转移
for (int i = ; i < sz; ++i) {
int next=t[si][i];
help.push(next);
vis[next] = ;
}
//bfs继续转移
for (int cnt = ; !help.empty();cnt++) {
int sz = help.size();
for (int i = ; i < sz; ++i) {
int next = help.front(); help.pop();
int nsz = node[next].size();
for (int t = ; t < nsz; ++t) {
int pnext = node[next][t];
if (vis[pnext] == )continue;
vis[pnext] = ;
cost[pnext][si] = cnt;
help.push(pnext);
}
}
}
} int main() {
int n, m, s, k;
scanf("%d %d %d %d", &n, &m, &s, &k);
int a0,a1;
for (int i = ; i <= n; ++i) {
scanf("%d", &a0);
t[a0].push_back(i);
}
for (int i = ; i < m; ++i) {
scanf("%d %d", &a0, &a1);
node[a0].push_back(a1);
node[a1].push_back(a0);
}
for (int i = ; i <= s; ++i) {
memset(vis, , sizeof vis);
bfs(i);
}
for (int i = ; i <= n; ++i) {
//排序并选择前k个
sort(cost[i] + , cost[i] + + s);
int sum = ;
for (int t = ; t <= k; ++t)
sum += cost[i][t];
printf("%d ", sum);
}
}

codeforces 987 D. Fair的更多相关文章

  1. codeforces 897A Scarborough Fair 暴力签到

    codeforces 897A Scarborough Fair 题目链接: http://codeforces.com/problemset/problem/897/A 思路: 暴力大法好 代码: ...

  2. CF 987 D. Fair

    D. Fair http://codeforces.com/contest/987/problem/D 题意: n个城镇m条道路,(保证没有重边,两个城镇间可以到达),每个城镇拥有的特产ai(可能多个 ...

  3. [Codeforces Round 486A] Fair

    [题目链接] https://codeforces.com/contest/986/problem/A [算法] 用dist(i,j)表示第i种食物运到第j个城市需要的最小代价 将所有特产为第i中食物 ...

  4. CodeForces 1084D The Fair Nut and the Best Path

    The Fair Nut and the Best Path 题意:求路径上的 点权和 - 边权和 最大, 然后不能存在某个点为负数. 题解: dfs一遍, 求所有儿子走到这个点的最大值和次大值. 我 ...

  5. CodeForces - 1073D Berland Fair

    XXI Berland Annual Fair is coming really soon! Traditionally fair consists of nnbooths, arranged in ...

  6. Codeforces 987 K预处理BFS 3n,7n+1随机结论题/不动点逆序对 X&Y=0连边DFS求连通块数目

    A /*Huyyt*/ #include<bits/stdc++.h> #define mem(a,b) memset(a,b,sizeof(a)) #define pb push_bac ...

  7. Codeforces 1083E The Fair Nut and Rectangles

    Description 有\(N\)个左下定点为原点的矩阵, 每个矩阵\((x_i,~y_i)\)都有一个数\(a_i\)表示其花费. 没有一个矩阵包含另一个矩阵. 现要你选出若干个矩阵, 使得矩阵组 ...

  8. Codeforces 1083B The Fair Nut and Strings

    Description 给定两个由 \('a'\), \('b'\) 组成的字符串 \(a\), \(b\),以及两个整数 \(n\) 和 \(k\) \(n\) 表示字符串 \(a\),\(b\) ...

  9. Codeforces 987 F - AND Graph

    F - AND Graph 思路: 首先,x & (~x) == 0 其次,~x 的 子集 y = ((~x) ^ (1<<k)), 0<= k < n(如果k这一位是 ...

随机推荐

  1. [原创]利用python构造ICMP Echo Request并发送

    import socket import struct def checksum(source_string): sum = 0 countTo = (len(source_string)/2)*2 ...

  2. Shr-前端汇总

    F7控件监听 f7控件的监听是指,在点击F7控件时,对控件内的内容进行选中后出发该事件监听:通过参数value可以获取当前F7控件的一些值信息. //人力编制方案监听 回写计划期间 及分录数据 ini ...

  3. verilog入门语法学习-第1篇

    1. 如何观察被测模块的响应: 在initial 块中,用系统任务$time 和 $monitor $time 返回当前的仿真时刻 $monitor 只要在其变量列表中有某一个或某几个变 量值发生变化 ...

  4. 获取项目中.txt 文件的内容

    package com.fh.controller.ruitai.util; import java.io.BufferedInputStream; import java.io.File; impo ...

  5. Java开发工程师(Web方向) - 03.数据库开发 - 第2章.数据库连接池

    第2章--数据库连接池 数据库连接池 一般而言,在实际开发中,往往不是直接使用JDBC访问后端数据库,而是使用数据库连接池的机制去管理数据库连接,来实现对后端数据库的访问. 建立Java应用程序到后端 ...

  6. LabVIEW初篇---前言

    最早接触labview,是研二的时候,2007年,当时为了补贴家用,改善生活.自己拿着本科毕业证去找工作,去一个企业面试,当时,面试的主考官,问了会什么吗,比如PLC.单片机啥的?那时候的自己,基本上 ...

  7. Matlab带比较方法的快排

    首先是主方法QUCIKSORT:(从小到大排列) function [A]=QUICKSORT(A,Low,high,mdat) set(,) if Low<high [A,w]=SPLITIO ...

  8. Caused by: java.lang.NoClassDefFoundError: javax/el/ELManager

    出现问题的原因: 在将springboot项目部署到Linux下的Tomcat中,项目无法正常启动(本地能正常运行),Tomcat启动日志中出现: Caused by: java.lang.NoCla ...

  9. C#通过gridview导出excel

    [CustomAuthorize]        public FileResult ExportQuestionCenterExcel(SearchBaseQuestion search)      ...

  10. c语言乐曲演奏——《千本樱》

    这个程序着实花费了我好长的时间,我本身对音乐一窍不通,先是跟着girl friend学习了简谱,根据c调44拍的<千本樱>写下了下面的程序. #include<stdio.h> ...