斯坦那树

百度释义

斯坦纳树问题是组合优化问题,与最小生成树相似,是最短网络的一种。最小生成树是在给定的点集和边中寻求最短网络使所有点连通。而最小斯坦纳树允许在给定点外增加额外的点,使生成的最短网络开销最小。

即最小斯坦那树即为并非选择所有的结点,而是选择一部分结点,为保证它们连通,且求解最小开销

题解

斯坦那树模板

发现直接表示点的存在性没有意义

设函数 \(f[i][state]\) 表示:对于点 \(i\),其它结点与其连通情况

那么有两种转移

其一、由其子集转移

\[f[i][state] = \min\limits_{sub \in state} \{f[i][sub] + f[i][\complement_{state}sub] - value_i\}
\]

之所以要减去 \(value_i\) 是因为会算重

附:枚举子集的方法

  1. for (int sub = state & (state - 1); sub; sub = (sub - 1) & state)

其二、由相邻当前状态下结点转移

\[f[i][state] = \min\limits_{state_p = true} \{f[p][state] + value_i\}
\]

发现很像三角形不等式,故考虑 \(SPFA\) 转移

总复杂度 \(O (n3^n + kE2^n)\),\(3^n\) 为枚举子集总复杂度

代码

  1. #include <iostream>
  2. #include <cstdio>
  3. #include <cstring>
  4. #include <queue>
  5. using namespace std;
  6. const int MAXN = 10 + 5;
  7. const int MAXM = 1 << 10;
  8. const int INF = 0x3f3f3f3f;
  9. const int NextX[4]= {- 1, 0, 0, 1}, NextY[4]= {0, - 1, 1, 0};
  10. int N, M;
  11. int Map[MAXN][MAXN]= {0};
  12. struct preSt {
  13. int x, y;
  14. int state;
  15. preSt (int fx = 0, int fy = 0, int fs = 0) :
  16. x (fx), y (fy), state (fs) {}
  17. } ;
  18. int f[MAXN][MAXN][MAXM];
  19. preSt pre[MAXN][MAXN][MAXM];
  20. int cnt = 0;
  21. queue<pair<int, int> > que;
  22. void SPFA (int state) {
  23. while (! que.empty()) {
  24. pair<int, int> top = que.front();
  25. que.pop();
  26. int x = top.first, y = top.second;
  27. for (int i = 0; i < 4; i ++) {
  28. int tx = x + NextX[i];
  29. int ty = y + NextY[i];
  30. if (tx < 1 || tx > N || ty < 1 || ty > M)
  31. continue;
  32. if (f[x][y][state] + Map[tx][ty] < f[tx][ty][state]) {
  33. f[tx][ty][state] = f[x][y][state] + Map[tx][ty];
  34. pre[tx][ty][state] = preSt (x, y, state);
  35. que.push(make_pair (tx, ty));
  36. }
  37. }
  38. }
  39. }
  40. int tag[MAXN][MAXN]= {0};
  41. void traceback (int x, int y, int state) {
  42. if (! x || ! y)
  43. return ;
  44. tag[x][y] = 1;
  45. preSt pr = pre[x][y][state];
  46. traceback (pr.x, pr.y, pr.state);
  47. if (pr.x == x && pr.y == y)
  48. traceback (pr.x, pr.y, state - pr.state);
  49. }
  50. int getnum () {
  51. int num = 0;
  52. char ch = getchar ();
  53. while (! isdigit (ch))
  54. ch = getchar ();
  55. while (isdigit (ch))
  56. num = (num << 3) + (num << 1) + ch - '0', ch = getchar ();
  57. return num;
  58. }
  59. int main () {
  60. memset (f, 0x3f, sizeof (f));
  61. N = getnum (), M = getnum ();
  62. int px, py;
  63. for (int i = 1; i <= N; i ++)
  64. for (int j = 1; j <= M; j ++) {
  65. Map[i][j] = getnum ();
  66. if (! Map[i][j]) {
  67. cnt ++, f[i][j][1 << (cnt - 1)] = 0;
  68. px = i, py = j;
  69. }
  70. }
  71. int limit = (1 << cnt) - 1;
  72. for (int state = 1; state <= limit; state ++) {
  73. for (int i = 1; i <= N; i ++)
  74. for (int j = 1; j <= M; j ++) {
  75. for (int sub = state & (state - 1); sub; sub = (sub - 1) & state) // from subset
  76. if (f[i][j][sub] + f[i][j][state - sub] - Map[i][j] < f[i][j][state]) {
  77. f[i][j][state] = f[i][j][sub] + f[i][j][state - sub] - Map[i][j];
  78. pre[i][j][state] = preSt (i, j, sub);
  79. }
  80. if (f[i][j][state] < INF)
  81. que.push(make_pair (i, j));
  82. }
  83. SPFA (state); // from other nodes
  84. }
  85. traceback (px, py, limit);
  86. printf ("%d\n", f[px][py][limit]);
  87. for (int i = 1; i <= N; i ++) {
  88. for (int j = 1; j <= M; j ++) {
  89. if (! Map[i][j])
  90. putchar ('x');
  91. else {
  92. tag[i][j] ? putchar ('o') : putchar ('_');
  93. }
  94. }
  95. puts ("");
  96. }
  97. return 0;
  98. }
  99. /*
  100. 4 4
  101. 0 1 1 0
  102. 2 5 5 1
  103. 1 5 5 1
  104. 0 1 1 0
  105. */

[WC2008]游览计划 「斯坦那树模板」的更多相关文章

  1. BZOJ_2595_[Wc2008]游览计划_斯坦纳树

    BZOJ_2595_[Wc2008]游览计划_斯坦纳树 题意: 分析: 斯坦纳树裸题,有几个需要注意的地方 给出矩阵,不用自己建图,但枚举子集转移时会算两遍,需要减去当前点的权值 方案记录比较麻烦,两 ...

  2. BZOJ2595 Wc2008 游览计划 【斯坦纳树】【状压DP】*

    BZOJ2595 Wc2008 游览计划 Description Input 第一行有两个整数,N和 M,描述方块的数目. 接下来 N行, 每行有 M 个非负整数, 如果该整数为 0, 则该方块为一个 ...

  3. 【BZOJ2595_洛谷4294】[WC2008]游览计划(斯坦纳树_状压DP)

    上个月写的题qwq--突然想写篇博客 题目: 洛谷4294 分析: 斯坦纳树模板题. 简单来说,斯坦纳树问题就是给定一张有边权(或点权)的无向图,要求选若干条边使图中一些选定的点连通(可以经过其他点) ...

  4. bzoj 2595 [Wc2008]游览计划(斯坦纳树)

    [题目链接] http://www.lydsy.com/JudgeOnline/problem.php?id=2595 [题意] 给定N*M的长方形,选最少权值和的格子使得要求的K个点连通. [科普] ...

  5. BZOJ2595 WC2008游览计划(斯坦纳树)

    斯坦纳树板子题. 考虑状压dp,设f[i][j][S]表示当前在点(i,j)考虑转移,其所在的联通块包含的关键点集(至少)为S的答案. 转移时首先枚举子集,有f[i][j][S]=min{f[i][j ...

  6. [WC2008]游览计划(斯坦纳树)

    [Luogu4294] 题解 : 斯坦纳树 \(dp[i][j]\) 表示以\(i\)号节点为根,当前状态为\(j\)(与\(i\)连通的点为\(1\)) 当根\(i\)不改变时状态转移方程是: \( ...

  7. BZOJ.2595.[WC2008]游览计划(DP 斯坦纳树)

    题目链接 f[i][s]表示以i为根节点,当前关键点的连通状态为s(每个点是否已与i连通)时的最优解.i是枚举得到的根节点,有了根节点就容易DP了. 那么i为根节点时,其状态s的更新为 \(f[i][ ...

  8. 【BZOJ2595】[Wc2008]游览计划 斯坦纳树

    [BZOJ2595][Wc2008]游览计划 Description Input 第一行有两个整数,N和 M,描述方块的数目. 接下来 N行, 每行有 M 个非负整数, 如果该整数为 0, 则该方块为 ...

  9. 【BZOJ 2595】2595: [Wc2008]游览计划 (状压DP+spfa,斯坦纳树?)

    2595: [Wc2008]游览计划 Time Limit: 10 Sec  Memory Limit: 256 MBSec  Special JudgeSubmit: 1572  Solved: 7 ...

随机推荐

  1. ElasticSearch 2 (13) - 深入搜索系列之结构化搜索

    ElasticSearch 2 (13) - 深入搜索系列之结构化搜索 摘要 结构化查询指的是查询那些具有内在结构的数据,比如日期.时间.数字都是结构化的.它们都有精确的格式,我们可以对这些数据进行逻 ...

  2. php实现文件上传,下载的常见文件配置

    配置文件,php.ini uploadfile  post_max_size 规定表单上传的最大文件:

  3. beta 圆桌 7

    031602111 傅海涛 1.今天进展 主界面微调,部分地方加入用户体验设计 2.存在问题 文档转化太久 3.明天安排 完成全部接口的交互 4.心得体会 文档转化优化不了 031602115 黄家雄 ...

  4. 简单封装DBUtils 和 pymysql 并实现简单的逆向工程生成class 类的py文件

    这里使用的 Python 版本是:Python 3.6.0b2. 涉及的三方库:DBUtils.pymysql 1.ConfigurationParser 通过调用Python内置的 xml.dom. ...

  5. robotframework 赋予临时id

    有的时候用rf执行ui自动化测试脚本的时候,一直提示找不到元素 (前提是没有id) 那么这个时候 我们可以随便赋予一个临时id Assign Id To Element      xpath=//*[ ...

  6. Mysql学习实践---SELECT INTO的替代方案

    从一个表复制数据,然后把数据插入到另一个新表中. 假设有一个已创建且有数据的orders表,要把orders表备份到还未创建的newOrders表里 SQL用法:SELECT * INTO newOr ...

  7. suoi16 随机合并试卷 (dp)

    算出来每个数被计算答案的期望次数就可以 考虑这个次数,我们可以把一次合并反过来看,变成把一个数+1然后再复制一个 记f[i][j]为一共n个数时第j个数的期望次数,就可以得到期望的递推公式,最后拿f[ ...

  8. BZOJ4589 Hard Nim(快速沃尔什变换FWT)

    这是我第一道独立做出来的FWT的题目,所以写篇随笔纪念一下. (这还要纪念,我太弱了) 题目链接: BZOJ 题目大意:两人玩nim游戏(多堆石子,每次可以从其中一堆取任意多个,不能操作就输).$T$ ...

  9. 【BZOJ 3451】Tyvj1953 Normal 思维题+期望概率+FFT+点分治

    我感觉是很强的一道题……即使我在刷专题,即使我知道这题是fft+点分治,我仍然做不出来……可能是知道是fft+点分治限制了我的思路???(别做梦了,再怎样也想不出来的……)我做这道题的话,一看就想单独 ...

  10. 5: EL 表达式小结

    1.EL表达式的语法格式很简单: 以前编写jsp代码时,如果要获取表单中的用户名,一般使用  <%=request.getParameter("name")%> ,这样 ...