双指针扫描 / 尺取法
来源:互联网 发布:最新熊片数据库 编辑:程序博客网 时间:2024/04/30 01:41
例①:
给定长度为n的整数数列以及整数S,求出总和不小于(>=)S的连续子串的长度的最小值,如果解不存在,输出0
分析:
代码:
int main(){ int n, s, a[10001]; //输入 cin >> n >> s; for(int i = 1; i <= n; ++i) cin >> a[i]; int l = 1, sum = 0, ans = inf;//初始化 for(int i = 1; i <= n; ++i)//线性扫描 { sum += a[i];//将a[i]加入sum if(sum >= s)//如果发现sum大于等于了s { while(sum >= s)//将sum减为小于s { sum -= a[l]; l++;//移动左指针,右指针是i } ans = min(ans,i - l + 1 + 1);//i - l + 1为区间[l,i]中元素的个数,由于使得sum小于了s,所以还要加1(相当于把不该删掉的元素加回来) } } cout << ans << endl;//打印 return 0;}
例②:
- 小明喜欢收集卡片,他要去商店购买新到的卡片。商店出售的卡片有N张,是连续的,小明只能购买连续的一段,这一串卡片共有M种,每种卡片都有一个价格,小明拿的钱数为V,他想知道如何用花最少的钱来集齐所有种类的卡片。
- N<=1000000 ,M<=2000 ,Ti<=2000 , V<=10^9
- 输入第1行 三个正整数 N,M,V,第2行共M个正整数,第i个数Ti表示第i种卡片的价格,第3行 N个正整数,表示第i个卡片是哪一类。
- 输出小明还剩多少钱
代码:
int cnt[2010],kind[1000010];//cnt[i]记录类型为i的卡片买的数量,kind[i]表示第i个卡片是哪一类,一定要将kind定义成全局变量int main(){ int n, m, v, t[2010]; //输入 cin >> n >> m >> v; for(int i = 1; i <= m; ++i) cin >> t[i]; for(int i = 1; i <= n; ++i) scanf("%d",&kind[i]); int SumOfKind = 0,sum = 0,l = 1,ans = inf;//初始化,SumOfKind记录已买到卡片的种类数,sum记录所花金钱,l为左指针,ans为答案,每次取较小值 for(int i = 1; i <= n; ++i)//线性扫描 { if(cnt[kind[i]] == 0)//如果第i张卡片所属种类还没有买过 SumOfKind++;//买下来,种类数+1 cnt[kind[i]]++;//张数+1 sum += t[kind[i]];//花费增加 while(cnt[kind[l]] > 1)//当发现左指针所指的卡片所属种类已经购买了多张 { sum -= t[kind[l]];//减去花费 cnt[kind[l]]--;//张数-1 l++;//左指针+1 } if(SumOfKind == m)//如果集齐了所有种类的卡片 ans = min(ans,sum);//更新答案 } cout << v - ans << endl; return 0;}
阅读全文
0 0
- 双指针扫描 / 尺取法
- poj-3061-Subsequence 尺取法/双指针法
- 双指针扫描
- 双指针扫描
- [hdu 5672][BestCoder Round #81 t3] String 尺取法||双指针法
- HDU 5056 双指针(也叫窗口滑动(也叫尺取法))
- 尺取法
- 尺取法
- 尺取法
- 尺取法
- 尺取法
- 尺取法
- 尺取法
- 尺取法
- 【尺取法】
- 尺取法
- 尺取法
- 尺取法
- Centos7 mysql-5.6.30-linux-glibc2.5-x86_64.tar.gz 安装
- .Net MVC4 发布后页面样式问题
- Google算法题:E-之字形遍历(zigzga)
- EXTJS框架中的日期控件在浏览器中的布满全屏问题的解决方案
- 剑指OFFER-二进制中1的个数
- 双指针扫描 / 尺取法
- imageloader帮助类
- 猴子摘桃--最长递增子串
- 使用AndroidImageSlider实现轮播
- 记录使用javascript中的一些坑
- Linux 常用命令
- 二叉树的四种遍历方式 (前序,中序,后序,层序遍历 python实现)
- Matlab直线最小二乘拟合实现
- 编程语言寿命预测