two point

来源:互联网 发布:不可而知 编辑:程序博客网 时间:2024/06/05 05:57

名字是zhw起的。
有这样一个问题:
这里写图片描述
解法:
利用两个指针,其中一个从前往后扫a数组,另一个从后往前扫b数组,先固定其中一个,另一个来扫
用可能成为最大值的数来更新答案。
具体看代码吧:

#include<iostream>#include<cstring>#include<algorithm>#include<cstdio>using namespace std;int n,p,ans;int a[100009],b[100009];int main(){    scanf("%d%d",&n,&p);    for(int i=1;i<=n;i++) scanf("%d",&a[i]);    for(int i=1;i<=n;i++) scanf("%d",&b[i]);    int t1=1,t2=n;    while(t1<=n&&t2>=1)    {        while(a[t1]+b[t2]>p&&t2>=1) t2--;        ans=max(ans,a[t1]+b[t2]);        t1++;    }    printf("%d",ans);    return 0;} 

这里写图片描述
解法:对a,b数组用two point,同时求c,d的最大前缀和(即前面的最大的那个数),不断更新答案。
代码:

#include<iostream>#include<cstring>#include<algorithm>#include<cstdio>#define M 100009using namespace std;int n,p,ans;int a[M],b[M],c[M],d[M];int main(){    scanf("%d%d",&n,&p);    for(int i=1;i<=n;i++) scanf("%d",&a[i]);    for(int i=1;i<=n;i++) scanf("%d",&b[i]);    for(int i=1;i<=n;i++) scanf("%d",&c[i]);    for(int i=1;i<=n;i++) scanf("%d",&d[i]);    for(int i=1;i<=n;i++) c[i]=max(c[i],c[i-1]),d[i]=max(d[i],d[i-1]);//前缀最大值        int t1=1,t2=n;    while(t1<=n&&t2>=1)    {        while(a[t1]+b[t2]>p&&t2>=1) t2--;        ans=max(ans,c[t1]+d[t2]);        t1++;    }     printf("%d",ans);    return 0;   }/*5 91 2 3 4 51 3 5 7 95 6 7 9 81 2 50 100 10*/
原创粉丝点击