Java C++ 算法leetcode828统计子串中唯一字符乘法原理

 更新时间:2022年09月14日 09:51:11   作者:AnjaVon  
这篇文章主要为大家介绍了Java C++ 算法leetcode828统计子串中唯一字符乘法原理详解,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步,早日升职加薪

题目要求

思路:模拟

解题的核心思想在于逆向思维,不考虑每个子数组中的唯一字符个数,转而考虑每个字符可以作为多少个子数组的唯一字符

  • 所以在计算答案时的算式和示例中给出的是不一样的;
  • 在计算每个字符“贡献”【即当前向左向右分别可组成的答案个数】的时候要用到乘法原理

对每一个字符s[i]s[i]s[i]都记录其左边和右边的第一个相同字符位置,分别记为l[i]l[i]l[i]和r[i]r[i]r[i],这两个位置中间构成的就是s[i]s[i]s[i]能够作为唯一字符的最长子串,在这个最长的子串中还有若干个较短的子串,此时s[i]s[i]s[i]的“贡献”可由到左边和到右边的距离相乘计算得出。

java

class Solution {
    public int uniqueLetterString(String s) {
        char[] cs = s.toCharArray();
        int n = cs.length, res = 0;
        int[] l = new int[n], r = new int[n];
        int[] letters = new int[26];
        Arrays.fill(letters, -1);
        for (int i = 0; i < n; i++) {
            int idx = cs[i] - 'A';
            l[i] = letters[idx]; // 左边第一个相同的字符所在位置
            letters[idx] = i; // 更新当前字母最新左位置
        }
        Arrays.fill(letters, n);
        for (int i = n - 1; i >= 0; i--) {
            int idx = cs[i] - 'A';
            r[i] = letters[idx]; // 右边第一个相同的字符所在位置
            letters[idx] = i; // 更新当前字母最新右位置
        }
        for (int i = 0; i < n; i++)
            res += (i - l[i]) * (r[i] - i);
        return res;
    }
}
  • 时间复杂度:O(n)
  • 空间复杂度:O(n)

C++

  • 因为memset初始化问题,所以在构成结果的时候多一步判断。
class Solution {
public:
    int uniqueLetterString(string s) {
        int n = s.size(), res = 0;
        cout << n << endl;
        int l[n], r[n];
        int letters[26];
        memset(letters, -1, sizeof(letters));
        for (int i = 0; i < n; i++) {
            int idx = s[i] - 'A';
            l[i] = letters[idx]; // 左边第一个相同的字符所在位置
            letters[idx] = i; // 更新当前字母最新左位置
        }
        memset(letters, -1, sizeof(letters));
        for (int i = n - 1; i >= 0; i--) {
            int idx = s[i] - 'A';
            r[i] = letters[idx]; // 右边第一个相同的字符所在位置
            letters[idx] = i; // 更新当前字母最新右位置
        }
        for (int i = 0; i < n; i++) {
            int ri = r[i] == -1 ? n : r[i];
            res += (i - l[i]) * (ri - i);
        }
        return res;
    }
};
  • 时间复杂度:O(n)
  • 空间复杂度:O(n)

Rust

  • 用Rust的遍历稍微改一下,思路一样……
impl Solution {
    pub fn unique_letter_string(s: String) -> i32 {
        let cs = s.as_bytes();
        (0..s.len()).into_iter().map(|i| {
            let (mut l, mut r) = (i - 1, i + 1);
            while l < s.len() && cs[l] != cs[i] {
                l -= 1;
            }
            while r < s.len() && cs[r] != cs[i] {
                r += 1;
            }
            ((i - l) * (r - i)) as i32
        }).sum::<i32>()
    }
}
  • 时间复杂度:O(n)
  • 空间复杂度:O(n)

以上就是Java C++ 算法leetcode828统计子串中唯一字符乘法原理的详细内容,更多关于Java C++ 统计子串唯一字符的资料请关注脚本之家其它相关文章!

相关文章

  • C++相交链表和反转链表详解

    C++相交链表和反转链表详解

    这篇文章主要介绍了C++相交链表和反转链表,结合实例形式分析了C++相交链表和反转链表的原理、实现方法及相关注意事项,需要的朋友可以参考下
    2021-08-08
  • VScode运行C++中文终端乱码的解决方案

    VScode运行C++中文终端乱码的解决方案

    这篇文章主要介绍了VScode运行C++中文终端乱码的解决方案,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教
    2023-01-01
  • C语言高效编程的几招小技巧

    C语言高效编程的几招小技巧

    这篇文章主要介绍了C语言高效编程的几招小技巧,本文讲解了以空间换时间、用数学方法解决问题以及使用位操作等编辑技巧,并给出若干方法和代码实例,需要的朋友可以参考下
    2015-05-05
  • C++中vector的常用接口详析说明

    C++中vector的常用接口详析说明

    vector类我们可以将其看作是一个能够动态扩容的数组,下面这篇文章主要给大家介绍了关于 C++ vector常用接口的相关资料,文中通过实例代码介绍的非常详细,需要的朋友可以参考下
    2022-08-08
  • C语言之直接插入排序算法的方法

    C语言之直接插入排序算法的方法

    这篇文章主要为大家介绍了C语言直接插入排序算法的方法,具有一定的参考价值,感兴趣的小伙伴们可以参考一下,希望能够给你带来帮助
    2021-12-12
  • C++实现LeetCode(211.添加和查找单词-数据结构设计)

    C++实现LeetCode(211.添加和查找单词-数据结构设计)

    这篇文章主要介绍了C++实现LeetCode(211.添加和查找单词-数据结构设计),本篇文章通过简要的案例,讲解了该项技术的了解与使用,以下就是详细内容,需要的朋友可以参考下
    2021-08-08
  • C++浅析内联函数的使用

    C++浅析内联函数的使用

    为了消除函数调用的时空开销,C++ 提供一种提高效率的方法,即在编译时将函数调用处用函数体替换,类似于C语言中的宏展开。这种在函数调用处直接嵌入函数体的函数称为内联函数(Inline Function),又称内嵌函数或者内置函数
    2022-05-05
  • C/C++中不定参数的使用详解

    C/C++中不定参数的使用详解

    这篇文章主要为大家详细介绍了C/C++中不定参数的使用的相关知识,文中的示例代码讲解详细,具有一定的借鉴价值,感兴趣的小伙伴可以跟随小编一起学习一下
    2023-12-12
  • 深入理解双指针的两种用法

    深入理解双指针的两种用法

    本篇文章是对双指针的两种用法进行了详细的分析介绍,需要的朋友参考下
    2013-05-05
  • C++ 之explicit关键字

    C++ 之explicit关键字

    今天我们来谈谈C++中的explicit关键字,这篇文章详细介绍了C语言的关键字explicit关键字,本文有详细的代码实例,感兴趣的同学可以借鉴参考
    2023-04-04

最新评论