python实现OD考试字符串基本问题汇总

我最近在复习OD考试时,汇总了一写字符串的基本算法,方便 OD考试的初学者

from collections import Counter

class Solution(object):

    """
    给定两个字符串 s 和 t ,编写一个函数来判断 t 是否是 s 的字母异位词。
    注意:若s 和 t中每个字符出现的次数都相同,则称s 和 t互为字母异位词
    """
    def isAnagram(self, s, t):
        """
            :type s: str
            :type t: str
            :rtype: bool
        """
        return sorted(s) == sorted(t)

    """
    给你一个字符串数组,请你将 字母异位词 组合在一起。可以按任意顺序返回结果列表。
    字母异位词 是由重新排列源单词的字母得到的一个新单词,所有源单词中的字母通常恰好只用一次
    输入: strs = ["eat", "tea", "tan", "ate", "nat", "bat"]
    输出: [["bat"],["nat","tan"],["ate","eat","tea"]]
    """
    def groupAnagrams(self, strs):
        """
             :type strs: List[str]
             :rtype: List[List[str]]
         """
        dic = {}  # 用字典进行存取
        for s in strs:  # 对每个字符串进行遍历
            keys = "".join(sorted(s))  # 对字符串进行正序排列
            print(keys)
            if keys not in dic:  # 只有一个的情况
                dic[keys] = [s]  # 要记得带中括号,否则下面不能使用append(),而且最后的输出也需要。
            else:  # 多个的情况
                dic[keys].append(s)
                print(dic[keys])
        print(dic)
        print(dic.values())
        print(list(dic.values()))

    """
    给定两个字符串s和 p,找到s中所有p的异位词的子串,返回这些子串的起始索引。不考虑答案输出的顺序。
    异位词 指由相同字母重排列形成的字符串(包括相同的字符串)
    输入: s = "cbaebabacd", p = "abc"
    输出: [0,6]
    解释:
    起始索引等于 0 的子串是 "cba", 它是 "abc" 的异位词。
    起始索引等于 6 的子串是 "bac", 它是 "abc" 的异位词。
    """
    def findAnagrams(self, s, p):
        p_count = Counter(p)  # 对字符串p中的字符进行计数
        s_count = Counter(s[:len(p) - 1])  # 对字符串s中前len(p)个字符进行计数
        ans = []  # 结果列表,用于保存s中p的易位词出现位置

        for i in range(len(p) - 1, len(s)):  # 从p的长度开始遍历到s的长度
            # s[i]从右边进入滑动窗口
            s_count[s[i]] += 1  # 更新字符计数器s_count中s[i]的出现次数
            cur_idx = i - len(p) + 1  # 滑动窗口左端元素在s中的位置
            cur_char = s[cur_idx]  # 滑动窗口左端元素

            # 易位词判别,比较窗口中字符串s[cur_idx:i]和目标字符串p是否互为易位词
            if s_count == p_count:
                ans.append(cur_idx)  # 如果是,则将滑动窗口左端位置加入到结果列表中

            s_count[cur_char] -= 1  # 将滑动窗口左端元素从窗口中弹出,更新字符计数器
            if s_count[cur_char] == 0:  # 如果弹出后计数器中出现次数变为零
                del s_count[cur_char]  # 从计数器中删除该字符
        return ans

    """
    如果在将所有大写字符转换为小写字符、并移除所有非字母数字字符之后,短语正着读和反着读都一样。则可以认为该短语是一个回文串 。
    输入:s = "race a car"
    输出:false
    解释:"raceacar" 不是回文串
    """
    def isPalindrome(self, s: str) -> bool:
        s_new = ''.join(i.lower() for i in s if i.isalnum())
        return s_new[::-1] == s_new

    """
    给你一个字符串 s,最多 可以从中删除一个字符。请你判断 s 是否能成为回文字符串:如果能,返回 true ;否则,返回 false
    输入:s = "abca"
    输出:true
    解释:你可以删除字符 'c'
    
    输入:s = "abc"
    输出:false
    """
    def validPalindrome(self, s: str) -> bool:
        l, r = 0, len(s) - 1
        while l <= r:
            if s[l] == s[r]:
                l += 1
                r -= 1
            else:
                j_1 = s[l + 1:r + 1]  # 删掉左边不等的进行判断,r+1是因为当前r代表的指针也是为判断的字符需要包含在内
                j_2 = s[l:r]  # 删掉右边不等的进行判断
                return j_1 == j_1[::-1] or j_2 == j_2[::-1]
        return 1 == 1

    """
    给你一个字符串 s,找到 s 中最长的回文子串
    输入:s = "babad"
    输出:"bab"
    解释:"aba" 同样是符合题意的答案。
    """
    def maxPalindromeString(sele,s):
        maxnum = 0
        if len(s) <= 2:
            return len(s), s
        for start in range(len(s)):
            for end in range(start + 1, len(s)):
                if end + 1 <= len(s) + 1 and s[start:end + 1] == s[start:end + 1][::-1]:
                    if len(s[start:end + 1]) >= maxnum:
                        maxnum = len(s[start:end + 1])
                        palindrome = s[start:end + 1]
        return maxnum, palindrome

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值