2021-11-05:摆动排序 II。给你一个整数数组 nums,将它重新排列成 nums[0] < nums[1] > nums[2] < nums[3]… 的顺序。你可以假设所有输入数组都可以得到满足题目要求的结果。力扣324。

福大大 答案2021-11-05:

需要了解快排和完美洗牌问题。
时间复杂度:O(N)。
空间复杂度:O(1)。

代码用golang编写。代码如下:

  1. package main
  2. import (
  3. "fmt"
  4. "math/rand"
  5. )
  6. func main() {
  7. nums := []int{1, 5, 1, 1, 6, 4}
  8. wiggleSort(nums)
  9. fmt.Println(nums)
  10. }
  11. // 时间复杂度O(N),额外空间复杂度O(1)
  12. func wiggleSort(nums []int) {
  13. if len(nums) < 2 {
  14. return
  15. }
  16. N := len(nums)
  17. // 小 中 右
  18. findIndexNum(nums, 0, len(nums)-1, N/2)
  19. if (N & 1) == 0 {
  20. // R L -> L R
  21. shuffle(nums, 0, len(nums)-1)
  22. // R1 L1 R2 L2 R3 L3 R4 L4
  23. // L4 R4 L3 R3 L2 R2 L1 R1 -> 代码中的方式,可以的!
  24. // L1 R1 L2 R2 L3 R3 L4 R4 -> 课上的分析,是不行的!不能两两交换!
  25. reverse(nums, 0, len(nums)-1)
  26. // 做个实验,如果把上一行的code注释掉(reverse过程),然后跑下面注释掉的for循环代码
  27. // for循环的代码就是两两交换,会发现对数器报错,说明两两交换是不行的, 必须整体逆序
  28. // for (int i = 0; i < nums.length; i += 2) {
  29. // swap(nums, i, i + 1);
  30. // }
  31. } else {
  32. shuffle(nums, 1, len(nums)-1)
  33. }
  34. }
  35. func findIndexNum(arr []int, L int, R int, index int) int {
  36. pivot := 0
  37. var range2 []int
  38. for L < R {
  39. //pivot = arr[L+(int)(Math.random()*(R-L+1))]
  40. pivot = arr[L+rand.Intn(R-L+1)]
  41. range2 = partition(arr, L, R, pivot)
  42. if index >= range2[0] && index <= range2[1] {
  43. return arr[index]
  44. } else if index < range2[0] {
  45. R = range2[0] - 1
  46. } else {
  47. L = range2[1] + 1
  48. }
  49. }
  50. return arr[L]
  51. }
  52. func partition(arr []int, L int, R int, pivot int) []int {
  53. less := L - 1
  54. more := R + 1
  55. cur := L
  56. for cur < more {
  57. if arr[cur] < pivot {
  58. less++
  59. //swap(arr, ++less, cur++);
  60. arr[less], arr[cur] = arr[cur], arr[less]
  61. cur++
  62. } else if arr[cur] > pivot {
  63. more--
  64. //swap(arr, cur, --more);
  65. arr[more], arr[cur] = arr[cur], arr[more]
  66. } else {
  67. cur++
  68. }
  69. }
  70. return []int{less + 1, more - 1}
  71. }
  72. func shuffle(nums []int, l int, r int) {
  73. for r-l+1 > 0 {
  74. lenAndOne := r - l + 2
  75. bloom := 3
  76. k := 1
  77. for bloom <= lenAndOne/3 {
  78. bloom *= 3
  79. k++
  80. }
  81. m := (bloom - 1) / 2
  82. mid := (l + r) / 2
  83. rotate(nums, l+m, mid, mid+m)
  84. cycles(nums, l-1, bloom, k)
  85. l = l + bloom - 1
  86. }
  87. }
  88. func cycles(nums []int, base int, bloom int, k int) {
  89. for i, trigger := 0, 1; i < k; i, trigger = i+1, trigger*3 {
  90. next := (2 * trigger) % bloom
  91. cur := next
  92. record := nums[next+base]
  93. tmp := 0
  94. nums[next+base] = nums[trigger+base]
  95. for cur != trigger {
  96. next = (2 * cur) % bloom
  97. tmp = nums[next+base]
  98. nums[next+base] = record
  99. cur = next
  100. record = tmp
  101. }
  102. }
  103. }
  104. func rotate(arr []int, l int, m int, r int) {
  105. reverse(arr, l, m)
  106. reverse(arr, m+1, r)
  107. reverse(arr, l, r)
  108. }
  109. func reverse(arr []int, l int, r int) {
  110. for l < r {
  111. arr[l], arr[r] = arr[r], arr[l]
  112. l++
  113. r--
  114. }
  115. }

执行结果如下:


左神java代码

2021-11-05:摆动排序 II。给你一个整数数组 nums,将它重新排列成 nums[0] < nums[1] > nums[2] < nums[3]... 的顺序。你可以假设所有输入数组都可以的更多相关文章

  1. Leetcode 324.摆动排序II

    摆动排序II 给定一个无序的数组 nums,将它重新排列成 nums[0] < nums[1] > nums[2] < nums[3]... 的顺序. 示例 1: 输入: nums ...

  2. Java实现 LeetCode 324 摆动排序 II

    324. 摆动排序 II 给定一个无序的数组 nums,将它重新排列成 nums[0] < nums[1] > nums[2] < nums[3]- 的顺序. 示例 1: 输入: n ...

  3. 2021.11.05 eleveni的水省选题的记录

    2021.11.05 eleveni的水省选题的记录 因为eleveni比较菜,但是eleveni不想写绿题(总不能说是被绿题虐得不想写),eleveni决定继续水noip原题. --实际上菜菜的el ...

  4. [LeetCode] 324. Wiggle Sort II 摆动排序 II

    Given an unsorted array nums, reorder it such that nums[0] < nums[1] > nums[2] < nums[3]... ...

  5. 324. 摆动排序 II(三路划分算法)

    题目: 给定一个无序的数组 nums,将它重新排列成 nums[0] < nums[1] > nums[2] < nums[3]... 的顺序. 示例 1: 输入: nums = [ ...

  6. LeetCode——324. 摆动排序 II

    给定一个无序的数组 nums,将它重新排列成 nums[0] < nums[1] > nums[2] < nums[3]... 的顺序. 示例 1: 输入: nums = [1, 5 ...

  7. 324 Wiggle Sort II 摆动排序 II

    给定一个无序的数组nums,将它重新排列成nums[0] < nums[1] > nums[2] < nums[3]...的顺序.例子:(1) 给定nums = [1, 5, 1, ...

  8. [Leetcode] 第324题 摆动排序II

    一.题目描述 给定一个无序的数组 nums,将它重新排列成 nums[0] < nums[1] > nums[2] < nums[3]... 的顺序. 示例 1: 输入: nums ...

  9. leetcode324 摆动排序II

      1. 首先考虑排序后交替插入 首尾交替插入,这种方法对于有重复数字的数组不可行: class Solution { public: void wiggleSort(vector<int> ...

  10. [Swift]LeetCode324. 摆动排序 II | Wiggle Sort II

    Given an unsorted array nums, reorder it such that nums[0] < nums[1] > nums[2] < nums[3]... ...

随机推荐

  1. vue 缓存后台获取的token

    代码 localStorage.setItem("token",res.data.data);// 用localStorage缓存token值

  2. Cmakelist如何添加自己的组件

    在components文件夹下添加各组件的CMakeList,其中可以设置的变量如下: COMPONENT_SRCS:要编译进当前组件的源文件的路径,推荐使用此方法向构建系统中添加源文件.COMPON ...

  3. Android笔记--基础的连接数据库的操作

    start.java package com.example.myapplication; import androidx.activity.result.ActivityResult; import ...

  4. 基于.Net开发的、支持多平台、多语言餐厅点餐系统

    今天给大家推荐一套支持多平台.多语言版本的订单系统,适合餐厅.酒店等场景. 项目简介 这是基于.Net Framework开发的,支持手机.平板.PC等平台.多语言版本开源的点餐系统,非常适合餐厅.便 ...

  5. Golang数据结构

    数据类型 不同类型的内存样式图 append,切片添加元素 清空切片的3种方法 清空切片的2种方法 查看变量类型 使用 fmt.Printf package main import "fmt ...

  6. Linux防火墙与端口操作命令

    CentOS 7系统 目录 1. 防火墙操作命令 2. 端口操作命令 3. CentOS 7 下安装firewall 1. 防火墙操作命令 序号 作用 命令 1 查看防火墙状态 systemctl s ...

  7. 内核不中断前提下,Gaussdb(DWS)内存报错排查方法

    摘要:本文主要讲解如何在内核保证操作不能中断采取的特殊处理,理论上用户执行的sql使用的内存(dynamic_used_memory) 是不会大范围的超过max_dynamic_memory的内存的 ...

  8. 【ACM算法竞赛日常训练】DAY5题解与分析【储物点的距离】【糖糖别胡说,我真的不是签到题目】| 前缀和 | 思维

    DAY5共2题: 储物点的距离(前缀和) 糖糖别胡说,我真的不是签到题目(multiset,思维) 作者:Eriktse 简介:19岁,211计算机在读,现役ACM银牌选手力争以通俗易懂的方式讲解算法 ...

  9. vue中关于对象的监听与数组的监听

    数组: 数组可监听到的方法:'push', 'pop', 'shift', 'unshift', 'splice', 'sort', 'reverse' 如果是根据索引改变值,需要使用vue.$set ...

  10. Ubuntu+uWSGI部署基于Django的API【鸿篇巨制,事无巨细】

    背景 任务: 视频翻译项目需要在两个服务器上进行通信(国内&海外的阿里服务器). 因为python是主语言,选用了Django 来快速部署API. 注:Django中文文档:https://d ...