随笔分类 -  算法--动态规划/贪心/基础算法

摘要:推荐论文:1.从一类单调性看算法的优化 汤泽2.关于DP的斜率优化http://wenku.baidu.com/view/d3d979dcd15abe23482f4d58.html3. 题目分析http://wenku.baidu.com/view/7745777801f69e3143329449.html4. 动态规划四之四边形不等式和斜率优化http://wenku.baidu.com/view/383d4de59b89680203d825a3.htmlCEOI 2004锯木厂选址预处理各前缀和,然后推出普通DP,然后利用决策单调性进行优化,证明过程有点忧伤,不妨跟着论文推推。#inclu 阅读全文
posted @ 2013-05-30 15:44 yefeng1627 阅读(2023) 评论(0) 推荐(0)
摘要:本质上是暴力模拟计算,逐位统计、以及如何寻找不被约束的状态来简化计算 是关键点。例题1 ural 1057. 1.树形结合, 按位统计. 若当前位为1, 则取0, 剩下的位任意取都比其小, ans += f[ L ][ k-tot ], L表示剩下长度. 论文这个地方写的感觉不对- -...#include#include#include#include#includeusing namespace std;int f[32][32];void init(){ memset(f,0,sizeof(f)); f[0][0] = 1; for(int i = 1; i ... 阅读全文
posted @ 2013-05-17 13:55 yefeng1627 阅读(1421) 评论(0) 推荐(0)
摘要:题意, 长度为n的序列, a1,a2, ...,ai, ..., an, 求最长严格上升子序列长度,与最长下降非严格自序列长度.解法: 首先不得不吐嘈下题目的读入,恶心指数上达5颗星. 对于一套拦截系统最多能拦截多少导弹, 求个非严格下降子序列就可以了.就不废话了. 主要还是求最少拦截数量. 有一个结论, 最少拦截系统数量为 严格上升子序列. 思路如下: 假定一个最长上升子序列形式如: ...a_i ... aj ... 对于 a_i 与 a_j 之间的数 x 只可能有两类, x <= a_i , 则可以 将这些导弹划分到 a_i拦截系统, x >= aj, 则可以将这些... 阅读全文
posted @ 2013-05-13 23:34 yefeng1627 阅读(372) 评论(0) 推荐(0)
摘要:NOI2010的一道动态规划,乌龟棋。线性的N个位置,每个位置有个权值,从1到N,给M个牌。每个牌在[1,4]范围。求最大权值和。最初考虑在用位置来表示状态,发现实在太多,无从下手. 后观摩别人思路后.发现竟然是从4种牌着手.4种牌使用的数量就已经确定了位置, 时间复杂度O(N^4), 一句话的题解..唉.还是太弱.拿到问题考虑的方向面还不够全. 以后要多注意发掘题目所给的数据以及题目的特性. 阅读全文
posted @ 2013-05-02 23:12 yefeng1627 阅读(131) 评论(0) 推荐(0)
摘要:题意: 一个串s,经过多次被覆盖,求最小的原串s.思路: 将题目转换下,就是 一个串s的前缀能覆盖串r,且s本身是r的一个后缀. 做法是首先考虑s的前缀能够覆盖r, 则我们从串r开始, 依次比较,并且记录上一次完全匹配(长度与s相同)的位置idx.当出现ri != sj时,令 j = nxt[j], (这样做,而不是直接令J=0,是为了保证模式串最短),因为可能是从头开始的. 继续比较,直到 j = 0, 意味着无法匹配.则将上一次的完全匹配位置idx+1到 i,添加到模式串s中, 然后更新模式串的next函数,因为我们已经知道了. s( 1, length ),这个时候模式串变成 s(... 阅读全文
posted @ 2013-04-30 11:21 yefeng1627 阅读(221) 评论(0) 推荐(0)
摘要:题意 求区间[a,b] 之间, x%f(x) = 0的数量, 其中f(x)表示x的数位和.解题思路: 转换成 F(A) = { x | x%f(x) = 0, 1 <= x <= A } , 然后结果即为 F(B)-F(A-1) 首先定义一个状态. dp( L, i, j, k ) 表示长度为L的数位和为i,其对j取模结果为k的方案数. 在同模j的情况下,则在该数后面增加一个x(0,9), 则得到 dp( L+1, i+x, j, (k*10+x)%j ). 那么转移方程就是: dp( L+1, i+x, j, (k*10+x)%j ) += dp( L, i, j, k ) .. 阅读全文
posted @ 2013-04-29 19:10 yefeng1627 阅读(343) 评论(0) 推荐(0)
摘要:题意: 给一个数字x, x<=1e18, 求其分解成数个fib数相加的方案总数.其中fib数不能重复.解题思路: 首先一个结论: 任意一个数,都能被分解成 数个fib数相加的形式. 另外, 在区间 [1,1e18]总共有 88个fib数. 对于一个数 x, 我们用一个长度为88的01序列来唯一表示.当前位为1则表示取,否则不取 例如 8: 00000100...0 2: 00100...0 3: 0110...0 从高位到低位. 根据 fib_i = fib_i-1 + fib_i-2 . 对于一个序列 001, 其能够被 110 替换. 我们可以总结出. 当前位为... 阅读全文
posted @ 2013-04-28 18:56 yefeng1627 阅读(154) 评论(0) 推荐(0)
摘要:题意: 两个都含有N个元素的数组a,b, 求 a[i]+b[j] ( i , j < N ) 的前 M个最小值(M < N)解题思路: 假定a,b数组都有序,则我们有下面的结论: a_1 + b_1 <= a_1 + b_2 <= ... <= a_1 + b_n a_2 + b_1 <= a_2 + b_2 <= ... <= a_2 + b_n ... a_n + b_1 <= a_n + b_2 <= ... <= a_n + b_n 那么我们就可以得出一个 N*N 的矩阵.如下形式 A(1,1), A(1,2), ... 阅读全文
posted @ 2013-04-28 16:10 yefeng1627 阅读(155) 评论(0) 推荐(0)
摘要:题意: 给一个N(n<=1e4), M个数字(长度为1),问最小的数x(x%n=0) 不包含这m个数。思路: 直接求,没想出解法. 对于一个数 x%n = m, 则 x` = x*10+i , 有 m` = (m*10+i)%n 我们可以利用 除了M个数字外的 数来构造这个 X. 因为需要最小的, 则其长度与字典序排列皆最小. 通过BFS进行搜索. 每一个 模n的余数之取第一次出现的,因为之后再出现的. 只可能更长或者更大. 必定不是最优解. 搜索节点,保存三个信息: 当前x的最后一位, 当前x%n的余数, 当前节点的父亲节点. 结果输出利用记忆父亲节点 ,然后递归输出即可.Vi... 阅读全文
posted @ 2013-04-24 17:07 yefeng1627 阅读(432) 评论(0) 推荐(0)
摘要:乱搞.#include<cstdio>#include<cstring>#include<cstdlib>#include<algorithm>#include<cmath>#include<stack>using namespace std;const double Pi = acos(-1);const double eps = 1e-8;char str[310][10];int n, m;int sign(double x){ return x<-eps?-1:(x>eps);}stack<dou 阅读全文
posted @ 2013-04-22 21:18 yefeng1627 阅读(162) 评论(0) 推荐(0)
摘要:题意 N个骑士,分别有个名字和战斗值。现在一个擂台上PK,第一个人上,之后的人一个一个上。若出现替换,则次数加1. 然后M次询问,每次一个K,问替换次数为K的序列,方案总数,以及字典序(骑士名)最小的方案输出。解题思路 DP优化总方案数 假定 p_1 < p_2 < ... < p_n 状态dp[i][k],表示前i个骑士已经分配完策略,这个时候放 j = [ i+1, n ] 中任一个。 当 p_j 放到 i+1 位置时, [ i+2, p-1 ] 中任意一个其实都不能替换掉 p_j , 则其在 [ i+2, n ] 这些位置可以随意放。 则我们得出转移方程... 阅读全文
posted @ 2013-04-16 21:18 yefeng1627 阅读(207) 评论(0) 推荐(0)
摘要:题意: n个单词,每行字符数量m个,单行字符数量值为j时,花费我 (m-j)^3 单词间有一个空格,问最小花费。 最后一行不花费解法 dp[i][j] 表示前i个单词,长度为j的最小花费 // 最后一行多余空格不作为计算,只有出现换行时才计算。// dp[i][j] 表示前i个单词,长度为j的最小整齐度// 由 dp[i][j] 通过添加一个 单词 L[i+1] 只可能导致两种情况// 1, 依然在一行,此时应满足条件 // 若 j == 0 ,则此时必定可以添加到后面有// dp[i+1][ L[i+1] ] = Min{ dp[i][j] }// 若 j > 0... 阅读全文
posted @ 2013-04-10 18:41 yefeng1627 阅读(155) 评论(0) 推荐(0)
摘要:题目大意 N件物品, 每件物品价值为a[i],数量为b[i], 问分成两堆差值尽量小.解题思路 感觉像是多重背包的变形~~~ 状态DP[N][V]表示,前i件物品,价值为V的方案数 转移方程 dp[i][ j+k*a[i] ] += dp[i-1][j] // k = 0..b[i] #include<stdio.h>#include<stdlib.h>#include<string.h>const int N = 250010;int dp[2][N];int main(){ int a[110], b[110], n; while( scanf(&quo 阅读全文
posted @ 2013-04-03 20:30 yefeng1627 阅读(201) 评论(0) 推荐(0)
摘要:题意 一个序列,求其所有长度为k的子序列最大最小值解法 单调队列维护最大最小。平摊时间复杂度到O(1)这题T了几次,因为C++,G++编译器不同的缘故。 感谢 纳米,科普。 具体见下yefeng1627(361072774) 19:06:28 求解 c++ 与 g++ (GUN c++)yefeng1627(361072774) 19:06:45 这个是为什么? 好像记得去年暑假HDU多校也有过这样的事情...yefeng1627(361072774) 19:06:53 有一题~~纳米(549950130) 19:07:05 所谓C++... 一般都是指VC..ye... 阅读全文
posted @ 2013-04-03 19:15 yefeng1627 阅读(204) 评论(0) 推荐(0)
摘要:题意 一个序列 a_1,a_2,..,a_n, 求最长子序列,满足 low <= max{ai}-min{ai} <= high.解题思路 首先考虑区间 [i,j], 我们可以通过固定右边界,来实现区间的滑动.以求解最佳值. 我们首先观察题目要求 low <= max{a_i,a_j}-min{a_i,a_j} <= high. 假定我们固定了右边界, 令 d = max{a_i,a_j} - min{a_i,a_j} 意味着我们只能移动 左边界i, 对于左边界的移动会导致两种情况 1. max{ a_i.a_j } 下降 2. min{ a_i, a_j } ... 阅读全文
posted @ 2013-04-03 15:46 yefeng1627 阅读(225) 评论(0) 推荐(0)
摘要:题意 有N根棍子,分别有长度。问将其拼接成X根,长度相同,求最小长度。解法 搜索。 1.因为总共n根棍子,最多拼接成n根相同长度, 并且,组成的棍子数量越多,则长度则越小 2.拼接的棍子数量必定能够 被 \sum{stick_i} 整除 3.若当前棍子长度 stick_i 不能够匹配, 在 stick_i = left_len 或者 stick_i = target_len 情况下, 此长度无合法方案, 因为每一根棍子都将被使用,若有一根不能被使用,则此长度方案必定不能成立.View Code #include<cstdio>#include<cstring>#incl 阅读全文
posted @ 2013-04-01 17:13 yefeng1627 阅读(147) 评论(0) 推荐(0)
摘要:题意: N个城市,由N-1条边连接, 有A,B两人占领i城市,花费分别为 A[i], B[i]. 相邻的则花费减半,(A占领城市x,则与x连通的城市,A再占领则只要A[x]/2, B类似)解法: dp[i][j][k] : 表示占领第 i 座城市, j = 0 则为 A占领 j = 1 则为 B占领 k = 0 则全部花费一半 k = 1 则其子孙节点中存在全额花费的 若此时遍历完 子节点 v,后回到其父节点 u . 有如下情况 一 对于 dp[u][0][0] , 第u个城市,由A占领,且子孙节点中由A占领的都是付 一半花费,可能有的情况 1. 以u为根的子树,全部... 阅读全文
posted @ 2013-03-28 18:48 yefeng1627 阅读(240) 评论(0) 推荐(0)
摘要:贴个官方解题报告Similarity of necklaces 2这个问题是一个012背包问题。我们知道01背包只要逆向线性检索,无限背包只要正向检索。012背包就是说,每个物品有一个数量上限。这个问题可以用log方法,也存在线性方法,需要维护一个递增/递减序列。我们先把所有的Table都放成下限,接下来我们可以算出它距离总和为0还需要增加多少。对于1<=i<=M,它可以看成这样一个物品:体积为Multi[i],费用为Pairs[i],数量为Up[i]-Low[i]。然后就得到一个012背包问题了。复杂度约为:O(M*背包大小)。其中背包大小不超过M*20*25=200*20*25 阅读全文
posted @ 2013-01-18 17:42 yefeng1627 阅读(353) 评论(0) 推荐(0)
摘要:大致思路是从根节点DFS下去后,处理完子树信息后,合并然后得出根节点信息,但是这一题子节点信息的合并确实比较棘手.如果我们尝试把从当前根节点走K步得到最大苹果数,划分为如下两种: go[t][i]代表节点t的所有子树上走i步不返回,取得的最大苹果数 bk[t][i]代表节点t的所有子树上走i步并返回,取得的最大苹果数 数组二维go,bkgo[t][i]代表节点t的所有子树上至多走i步不返回,取得的最大苹果数bk[t][i]代表节点t的所有子树上至多走i步并返回,取得的最大苹果数求节点为x,实行不断合并子树求最优值当前合并到了q棵子树:go[x][i]就是这q棵子树上至多走i步不返... 阅读全文
posted @ 2013-01-17 22:21 yefeng1627 阅读(309) 评论(0) 推荐(0)
摘要:对于一颗以 rt 为根的树,其有 I 个子节点分别为 S1,S2,。。。,SI ,则 状态 dp(i,j)表示前 1,2,,,,,I 子树,组合而成一棵 包含 J个节点的 子树的最小花费 sum(Si) 表示 以 Si 节点为根的子树,节点数量 Cut (Si, K) 表示 子树 Si 中取得 一棵包含 根Si 的子树 且节点数量为 K 的最小花费 则状态转移方程: 其中 x <= Sum(Si), 且 注意到, 其实我们已经把 子树S1,S2,,S(i-1) 合并到了 dp(I-1)里头去了。这样就简化了枚举计算。 另外,还可以注意到 ... 阅读全文
posted @ 2013-01-17 17:12 yefeng1627 阅读(371) 评论(0) 推荐(0)

Launch CodeCogs Equation Editor