双指针算法、位运算

简介: 双指针算法、位运算

双指针算法模板:


for (int i = 0, j = 0; i < n; i ++ ){while (j < i && check(i, j)) j ++ ;// 具体问题的逻辑}


常见问题分类:


(1) 对于一个序列,用两个指针维护一段区间

(2) 对于两个序列,维护某种次序,比如归并排序中合并两个有序序列的操作


最长连续不重复子序列


https://www.acwing.com/problem/content/801/


    final static int N=100010;
    public static void main(String[] args) throws IOException {
        int []arr=new int[N];
        BufferedReader br=new BufferedReader(new InputStreamReader(System.in));
        int n=Integer.parseInt(br.readLine().split(" ")[0]);
        String []str=br.readLine().split(" ");
        for (int i = 0; i < n; i++) {
            arr[i]=Integer.parseInt(str[i]);
        }
        int []s=new int[N];
        int max=0;
        for(int i=0,j=0;i<n;i++){
           s[arr[i]]++;
           while (j<i &&s[arr[i]]>1){
               s[arr[j]]--;
               j++;
           }
            max=Math.max(max,i-j+1);
        }
        System.out.println(max);
    }


数组元素的目标和

https://www.acwing.com/problem/content/802/


    final static int N=100010;
    public static void main(String[] args) throws IOException {
        int[] arrN = new int[N];
        int[] arrM = new int[N];
        BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
        String s= br.readLine();
        int n = Integer.parseInt(s.split(" ")[0]);
        int m = Integer.parseInt(s.split(" ")[1]);
        int x = Integer.parseInt(s.split(" ")[2]);
        String []s1= br.readLine().split(" ");
        for (int i = 0; i < n; i++) {
            arrN[i]=Integer.parseInt(s1[i]);
        }
        String []s2= br.readLine().split(" ");
        for (int i = 0; i < m; i++) {
            arrM[i]=Integer.parseInt(s2[i]);
        }
        br.close();
        for(int i=0,j=m-1;i<n;i++){
            while (j>0 &&arrN[i]+arrM[j]>x){
                j--;
            }
           if(arrN[i]+arrM[j]==x){
               System.out.println(i+" "+j);
               break;
           }
        }
    }


判断子序列


https://www.acwing.com/problem/content/2818/

 final static int N=100010;
    public static void main(String[] args) throws IOException {
        int[] a = new int[N];
        int[] b = new int[N];
        BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
        String []s= br.readLine().split(" ");
        int n=Integer.parseInt(s[0]),m=Integer.parseInt(s[1]);
        String []s1= br.readLine().split(" ");
        for (int i = 0; i < n; i++) {
            a[i]=Integer.parseInt(s1[i]);
        }
        String []s2= br.readLine().split(" ");
        for (int i = 0; i < m; i++) {
            b[i]=Integer.parseInt(s2[i]);
        }
        int i = 0, j = 0;
        while(i < n && j < m){
            if(a[i] == b[j]) i ++;
            j ++;
        }
        if(i == n) System.out.println("Yes");
        else System.out.println("No");
    }


位运算:


二进制中1的个数


https://www.acwing.com/problem/content/803/

按位与:a&b是把a和b都转换成二进制数然后再进行与的运算;

进入正题


二进制中1的个数,


本题是通过找出x的二进制位中最末尾出现的1的位置,用二进制表示出来


假设 x = 9 即 0 1001,-x为x的反码+1


-x = ~x + 1即1 0111 =>1 0110 + 1 =1 0111


x & -x


0 1001


& 1 0111


————————————


0 0001


用x - (x&-x) = 1000,这样我们即得到了一个1,同时将该1的位置从数x中去除


public static void main(String[] args) throws IOException {
        BufferedReader br=new BufferedReader(new InputStreamReader(System.in));
        String []s=br.readLine().split(" ");
        int n=Integer.parseInt(s[0]);
        String []s1=br.readLine().split(" ");
        int x=0;
        for (int i = 0; i < n; i++) {
            x=Integer.parseInt(s1[i]);
            int count=0;
            while (x!=0){
                x-=lowbit(x);
                count++;
            }
            System.out.print(count+" ");
        }
    }
    public static int lowbit(int x){
        return x&-x;
    }
相关文章
|
23天前
|
算法 数据处理 C语言
C语言中的位运算技巧,涵盖基本概念、应用场景、实用技巧及示例代码,并讨论了位运算的性能优势及其与其他数据结构和算法的结合
本文深入解析了C语言中的位运算技巧,涵盖基本概念、应用场景、实用技巧及示例代码,并讨论了位运算的性能优势及其与其他数据结构和算法的结合,旨在帮助读者掌握这一高效的数据处理方法。
34 1
|
4月前
|
算法
【算法】位运算算法——消失的两个数字(困难)
【算法】位运算算法——消失的两个数字(困难)
|
4月前
|
算法
【算法】位运算算法——只出现一次的数字Ⅱ
【算法】位运算算法——只出现一次的数字Ⅱ
|
4月前
|
算法
【算法】位运算算法——判断字符是否唯一
【算法】位运算算法——判断字符是否唯一
|
3月前
|
算法 索引 容器
双指针算法详解
本文介绍了双指针算法及其应用。双指针算法是在数组或字符串中常用的高效技术,通过维护两个指针遍历数据结构以解决特定问题。根据指针移动方向,可分为同向双指针、相向双指针和快慢指针。同向双指针如移动零和复写零问题;快慢指针如快乐数问题;相向双指针如盛水最多的容器、有效三角形数量及多数之和等问题。通过合理运用双指针技巧,可简化代码并提高效率。
73 4
双指针算法详解
|
2月前
|
算法 C++
【算法】双指针+二分(C/C++
【算法】双指针+二分(C/C++
|
2月前
|
搜索推荐 C语言 C++
【C语言】指针篇-精通库中的快速排序算法:巧妙掌握技巧(4/5)
【C语言】指针篇-精通库中的快速排序算法:巧妙掌握技巧(4/5)
|
4月前
|
算法
【算法】位运算算法——两整数之和
【算法】位运算算法——两整数之和
|
4月前
|
算法
【算法】位运算算法——丢失的数字
【算法】位运算算法——丢失的数字