双指针算法

核心用途:将朴素算法优化 (所有双指针算法的时间复杂度都是O(n)

例1:输入字符串,空格隔开单词,输出每一个单词
#include<iostream>
#include<string.h>
using namespace std;
int main(){
    char str[1000];
    
    gets(str);
    
    for(int i = 0; i<n; i++ ){
        int j=i;//j指向i所在的地方
        while(j<n && str[j]!=' ')j++;//j没有越界且j指向的位置不是空格时,j移动
        
         for(int k=i;k<j;k++)cout<<str[k];//输出i,j之间的字母,此时i指向单词的开始,j指向空格
        cout<<endl
        
         i=j;//i指向空格处
        //本次循环结束后,i++,i指向下一个单词的开始
    }
    return 0;
}
例2 :P 799,最长连续不重复子序列

双指针算法一般先从暴力开始想,最后用双指针进行优化

先枚举终点,再枚举起点

i是终点,j是起点

#include<iostream>

using namespace std;
const int N=100010;

int n;
int a[N];
int s[N];//存了当前【j,i】这个区间里面,每个数出现的次数

int main(){
    cin >> n;
    for(int i=0; i<n; i++) cin >> a[i];
    
    int res = 0;
    for(int i = 0, j = 0; i < n; i++ ){
        s[a[i]]++;//记录a[i]这个数出现的次数
        while(s[a[i]]> 1){
            //如果这个数出现两遍,j就开始右移,直到i,j指向同一个数
            s[a[j]]--;//每一个都减减,是为了j移动到重复数字前面那个数字的时候时,s[a[i]]--,可以跳出循环
            j++;//此时i,j指向同一个位置
        }
        res = max(res, i-j+1);
    }
    cout << res <<endl;
    return 0;
}
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值