当前位置: 首页 > article >正文

解决 LeetCode 922 题:按奇偶排序数组 II

解决 LeetCode 922 题:按奇偶排序数组 II

题目描述

给定一个非负整数数组 nums,其中一半整数是奇数,一半整数是偶数。要求对数组进行排序,以便当 nums[i] 为奇数时,i 也是奇数;当 nums[i] 为偶数时,i 也是偶数。

你可以返回任何满足上述条件的数组作为答案。

示例

示例 1

输入:

nums = [4, 2, 5, 7]

输出:

[4, 5, 2, 7]

解释:[4,7,2,5],[2,5,4,7][2,7,4,5] 也会被接受。

示例 2

输入:

nums = [2, 3]

输出:

[2, 3]

提示

  • 2 <= nums.length <= 2 * 10^4
  • nums.length 是偶数
  • nums 中一半是偶数
  • 0 <= nums[i] <= 1000

思路分析

1. 基本思路

给定一个数组 nums,题目要求将数组中的偶数放在所有偶数索引位置(即偶数下标),将奇数放在所有奇数索引位置。由于题目给定了一个条件:数组中一半是奇数,一半是偶数,因此,我们只需要将所有偶数和奇数分开并分别放置到合适的索引位置。

2. 如何分配偶数和奇数?

  • 遍历整个数组,找出其中的偶数和奇数。
  • 使用两个数组 evenodd 分别存放偶数和奇数。
  • 然后将 even 中的偶数按照偶数索引(0, 2, 4, …)放入结果数组,将 odd 中的奇数按照奇数索引(1, 3, 5, …)放入结果数组。

3. 时间复杂度

  • 遍历数组的时间复杂度为 O(n),其中 n 是数组的长度。
  • 每次操作都只需要常数时间,因此总的时间复杂度为 O(n)

4. 空间复杂度

  • 我们使用了两个额外的数组 evenodd,所以空间复杂度是 O(n)

代码实现

class Solution:
    def sortArrayByParityII(self, nums: List[int]) -> List[int]:
        n = len(nums)
        even = []  # 存储偶数
        odd = []   # 存储奇数
        res = []   # 最终结果数组
        
        # 将偶数和奇数分开
        for num in nums:
            if num % 2 == 0:
                even.append(num)
            else:
                odd.append(num)
        
        # 将偶数和奇数分别放到合适的位置
        for i in range(n // 2):
            res.append(even[i])  # 偶数放在偶数位置
            res.append(odd[i])   # 奇数放在奇数位置
        
        return res

代码解释

  1. 初始化:

    • n = len(nums) 获取数组的长度。
    • evenodd 数组分别用于存储偶数和奇数。
    • res 数组用于存放最终的结果。
  2. 遍历数组:

    • 使用 for num in nums 遍历数组中的每个元素。
    • 判断当前元素是偶数还是奇数,将偶数放入 even 数组,将奇数放入 odd 数组。
  3. 填充结果数组:

    • 使用 for i in range(n // 2) 遍历每个偶数位置。
    • 在每个偶数位置放入 even[i],在每个奇数位置放入 odd[i]
  4. 返回结果:

    • 最终返回 res 数组,即按奇偶排序后的数组。

优化建议

进阶:在原地操作,减少空间使用

题目要求我们使用更少的额外空间。可以使用原地交换的方法来解决问题,不需要额外创建新的数组。

优化思路:

  • 我们可以直接在原数组 nums 中进行交换。
  • 使用两个指针 even_indexodd_index,分别指向数组中的偶数位置和奇数位置。
  • 如果当前 even_index 位置不是偶数,就与下一个偶数交换;如果当前 odd_index 位置不是奇数,就与下一个奇数交换。

代码实现(原地交换)

class Solution:
    def sortArrayByParityII(self, nums: List[int]) -> List[int]:
        even_index = 0  # 偶数位置
        odd_index = 1   # 奇数位置
        
        while even_index < len(nums) and odd_index < len(nums):
            if nums[even_index] % 2 == 0:
                even_index += 2  # 如果当前偶数位置是偶数,直接跳到下一个偶数位置
            elif nums[odd_index] % 2 != 0:
                odd_index += 2  # 如果当前奇数位置是奇数,直接跳到下一个奇数位置
            else:
                # 如果当前偶数位置是奇数,当前奇数位置是偶数,交换它们
                nums[even_index], nums[odd_index] = nums[odd_index], nums[even_index]
                even_index += 2
                odd_index += 2
        
        return nums

代码解析

  • 偶数和奇数指针:

    • even_index = 0odd_index = 1,分别指向数组中的偶数和奇数位置。
  • 遍历交换:

    • even_index 指向偶数,odd_index 指向奇数时,如果它们不满足条件(偶数位置不是偶数,奇数位置不是奇数),就交换它们。
  • 返回结果:

    • 返回修改后的 nums 数组,直接在原数组上进行操作。

总结

本题要求对数组按奇偶排序,最直接的方法是通过两个数组分别存放偶数和奇数,然后按照位置填充。然而,考虑到空间复杂度问题,我们可以通过双指针的方式在原地交换数组,减少额外的空间使用。

通过这样的思路,我们可以在 O(n) 时间内完成问题的求解,且空间复杂度可以优化到 O(1),提高算法的效率。


http://www.kler.cn/a/533090.html

相关文章:

  • 8.原型模式(Prototype)
  • DeepSeek最新图像模型Janus-Pro论文阅读
  • Kafka分区策略实现
  • 介绍一下Mybatis的Executor执行器
  • Starrocks 对比 Clickhouse
  • 【PyQt】getattr动态访问对象的属性
  • Linux 传输层协议 UDP 和 TCP
  • FPM(Effing Package Management)安装与使用指南
  • B-树:解锁大数据存储和与快速存储的密码
  • 基于JavaWeb开发的Java+Jsp+SpringMVC漫威手办商城系统设计和实现
  • 1分钟基于腾讯云TI平台搭建DeepSeek大模型
  • 2025-2-3-sklearn学习(50) (51) 完结篇 零落成泥碾作尘,只有香如故。
  • Vite:现代前端开发的利器
  • Spring Security(maven项目) 3.0.3.0版本
  • 接口测试通用测试用例
  • 深度剖析八大排序算法
  • 【MySQL — 数据库基础】深入解析MySQL的约束操作
  • 如何获取sql数据中时间的月份、年份(类型为date)
  • 【大数据技术】本机PyCharm远程连接虚拟机Python
  • 【电脑系统】电脑突然(蓝屏)卡死发出刺耳声音
  • 第 11 课 Python 多线程
  • idea中git的简单使用
  • 基于RK3588/RK3576+MCU STM32+AI的储能电站电池簇管理系统设计与实现
  • OpenAI的第二个AI Agent:Deep Research完全解读!
  • CTFSHOW-WEB入门-命令执行71-77
  • 【C++】STL——vector底层实现