算法题解合集:回文子串、不相邻取数、空调遥控

在算法学习和刷题过程中,我们会遇到各种有趣的题目,今天就来分享三道不同类型题目的解法思路,分别是回文子串最短长度不相邻取数最大和空调遥控最佳温度区间


一、回文子串最短长度(小红的字符串)

题目描述

小红拿到一个只包含 'a''b''c'三种字符的字符串。她想知道,这个字符串最短的、长度超过1的回文子串的长度是多少?

  • 子串定义:字符串中取一段连续 的区间(例如 "abcca"的子串有 "ab""bcca"等,但 "aca"不是子串)。

  • 回文定义:正着读和倒着读都相同的字符串(例如 "aa""aba")。

  • 若不存在长度超过1的回文子串,输出 -1

解题思路

由于字符串只包含 'a''b''c'三种字符,最短的回文子串长度只能是 2 或 3

  • 长度为 2 的回文子串:两个相同字符(如 "aa""bb""cc")。

  • 长度为 3 的回文子串:首尾字符相同(如 "aba""bcb")。

因此,我们只需要枚举所有二元组(长度2的子串)三元组(长度3的子串),判断是否为回文,找到最短的那个即可。

代码实现(Python)

复制代码
def shortest_palindrome(s):
    n = len(s)
    # 先检查所有长度为2的子串
    for i in range(n - 1):
        if s[i] == s[i + 1]:
            return 2
    # 再检查所有长度为3的子串
    for i in range(n - 2):
        if s[i] == s[i + 2]:
            return 3
    # 没有符合条件的回文子串
    return -1

# 测试示例
print(shortest_palindrome("abcca"))  # 输出2("cc"是回文)
print(shortest_palindrome("abcab"))  # 输出-1(无长度>1的回文)

二、不相邻取数(动态规划 - 线性DP)

题目描述

小红拿到一个数组,想取一些不相邻的数,使得取出的数之和尽可能大。请帮助她求出这个最大和。

  • 输入:第一行是正整数 n(数组长度),第二行是 n个正整数 a_i

  • 输出:不相邻数的最大和。

解题思路

这是经典的**"打家劫舍"型动态规划问题** 。设 dp[i]表示前 i个元素中,不相邻取数的最大和。

状态转移方程:

  • 对于第 i个元素(i >= 2),有两种选择:

    • 不选第 i个元素:dp[i] = dp[i-1](继承前 i-1个的最大和)。

    • 选第 i个元素:dp[i] = dp[i-2] + a[i](前 i-2个的最大和 + 第 i个元素)。

  • 因此,dp[i] = max(dp[i-1], dp[i-2] + a[i])

边界条件:

  • dp[0] = a[0](只有一个数时,最大和是它本身)。

  • dp[1] = max(a[0], a[1])(两个数时,选较大的那个)。

代码实现(Python)

复制代码
def max_non_adjacent_sum(nums):
    n = len(nums)
    if n == 0:
        return 0
    if n == 1:
        return nums[0]
    # 初始化dp数组
    dp = [0] * n
    dp[0] = nums[0]
    dp[1] = max(nums[0], nums[1])
    for i in range(2, n):
        dp[i] = max(dp[i-1], dp[i-2] + nums[i])
    return dp[-1]

# 测试示例
nums = [2, 6, 4, 1]
print(max_non_adjacent_sum(nums))  # 输出7(选6和1)

三、空调遥控(二分 / 滑动窗口)

题目描述

集训室有 n名队员,每位队员的温度诉求为 a[i]。当室内温度为 K时,若 |a[i] - K| ≤ p,队员能正常训练;否则会躁动。求最佳情况下,最多能有多少队员同时进入训练状态

解题思路

方法一:滑动窗口(排序后)
  1. 排序 :将温度诉求数组 a排序,方便后续窗口操作。

  2. 滑动窗口 :维护一个窗口 [left, right],使得窗口内的**最大值 - 最小值 ≤ 2p *(因为 |a[i]-K| ≤ p等价于 K ∈ [a[i]-p, a[i]+p],所以窗口内所有数必须在同一个长度为 2*p的区间内)。

  3. 统计最大窗口大小:窗口越大,满足条件的队员越多。

方法二:二分查找
  1. 排序:同样先对数组排序。

  2. 二分枚举答案 :假设最多能满足 k名队员,判断是否存在一个长度为 k的连续子数组,其最大值 - 最小值 ≤ 2*p。

  3. 验证函数 :对于每个可能的 k,用二分法找是否存在这样的子数组。

代码实现(Python - 滑动窗口)

复制代码
def max_trainers(a, p):
    a.sort()
    n = len(a)
    left = 0
    max_len = 0
    for right in range(n):
        # 收缩左边界,直到窗口内最大值-最小值 ≤ 2*p
        while a[right] - a[left] > 2 * p:
            left += 1
        # 更新最大窗口长度
        max_len = max(max_len, right - left + 1)
    return max_len

# 测试示例
n, p = 6, 2
a = [1, 5, 3, 2, 4, 6]
print(max_trainers(a, p))  # 输出5(温度调为3或4时,5人满足)

总结

这三道题分别覆盖了字符串处理动态规划滑动窗口/二分查找三种经典算法思路:

  • 回文子串:利用字符种类少的特性,枚举短子串。

  • 不相邻取数:线性DP的典型应用(打家劫舍模型)。

  • 空调遥控:排序后用滑动窗口或二分查找优化区间问题。

通过这类题目练习,可以加深对算法思路的理解,提升代码实现能力~ 🚀

相关推荐
Dxy123931021624 分钟前
Django 数据库 ENGINE 完全指南:选错了,性能差 10 倍
python·django
码不停蹄的玄黓36 分钟前
Java 生产者-消费者模型详解
java·开发语言·python
凯瑟琳.奥古斯特1 小时前
力扣1235:加权区间调度最优解
java·python·算法·leetcode·职场和发展
郑洁文2 小时前
基于Python的网络入侵检测系统
网络·python·php
AIMath~2 小时前
python中的uv命令揭秘
开发语言·python·uv
弹简特2 小时前
【零基础学Python】06-Python模块和包、异常处理、文件常用操作
开发语言·python
念恒123062 小时前
Python 面向对象编程核心:对象、实例化、封装与变量作用域
开发语言·python
薛定谔的悦2 小时前
光伏-储能-负荷联合预测:给 EMS 装上“预知能力“
java·数据库·人工智能·python·储能
Metaphor6923 小时前
使用 Python 在 Excel 中查找并高亮显示
python·信息可视化·excel
旦莫4 小时前
AI测试Agent的两种架构路径:谁做主控?
人工智能·python·架构·自动化·ai测试