mirror of
https://github.com/chefyuan/algorithm-base.git
synced 2026-03-11 04:14:41 +00:00
添加了python版本代码
为数据结构和算法文件夹下的代码增加了python语言版本
This commit is contained in:
@@ -36,7 +36,7 @@
|
||||
|
||||
下面我们先来介绍下挖坑填数的分区方法
|
||||
|
||||
基本思想是我们首先以序列的第一个元素为基准数,然后将该位置挖坑,下面判断 nums[hight] 是否大于基准数,如果大于则左移 hight 指针,直至找到一个小于基准数的元素,将其填入之前的坑中,则 hight 位置会出现一个新的坑,此时移动 low 指针,找到大于基准数的元素,填入新的坑中。不断迭代直至完成分区。
|
||||
基本思想是我们首先以序列的第一个元素为基准数,然后将该位置挖坑,下面判断 nums[high] 是否大于基准数,如果大于则左移 high 指针,直至找到一个小于基准数的元素,将其填入之前的坑中,则 high 位置会出现一个新的坑,此时移动 low 指针,找到大于基准数的元素,填入新的坑中。不断迭代直至完成分区。
|
||||
|
||||
大家直接看我们的视频模拟吧,一目了然。
|
||||
|
||||
@@ -46,6 +46,8 @@
|
||||
|
||||
是不是很容易就理解啦,下面我们直接看代码吧。
|
||||
|
||||
Java Code:
|
||||
|
||||
```java
|
||||
class Solution {
|
||||
public int[] sortArray(int[] nums) {
|
||||
@@ -54,30 +56,30 @@ class Solution {
|
||||
return nums;
|
||||
|
||||
}
|
||||
public void quickSort (int[] nums, int low, int hight) {
|
||||
public void quickSort (int[] nums, int low, int high) {
|
||||
|
||||
if (low < hight) {
|
||||
int index = partition(nums,low,hight);
|
||||
if (low < high) {
|
||||
int index = partition(nums,low,high);
|
||||
quickSort(nums,low,index-1);
|
||||
quickSort(nums,index+1,hight);
|
||||
quickSort(nums,index+1,high);
|
||||
}
|
||||
|
||||
}
|
||||
public int partition (int[] nums, int low, int hight) {
|
||||
public int partition (int[] nums, int low, int high) {
|
||||
|
||||
int pivot = nums[low];
|
||||
while (low < hight) {
|
||||
while (low < high) {
|
||||
//移动hight指针
|
||||
while (low < hight && nums[hight] >= pivot) {
|
||||
hight--;
|
||||
while (low < high && nums[high] >= pivot) {
|
||||
high--;
|
||||
}
|
||||
//填坑
|
||||
if (low < hight) nums[low] = nums[hight];
|
||||
while (low < hight && nums[low] <= pivot) {
|
||||
if (low < high) nums[low] = nums[high];
|
||||
while (low < high && nums[low] <= pivot) {
|
||||
low++;
|
||||
}
|
||||
//填坑
|
||||
if (low < hight) nums[hight] = nums[low];
|
||||
if (low < high) nums[high] = nums[low];
|
||||
}
|
||||
//基准数放到合适的位置
|
||||
nums[low] = pivot;
|
||||
@@ -107,26 +109,26 @@ class Solution {
|
||||
|
||||
}
|
||||
|
||||
public void quickSort (int[] nums, int low, int hight) {
|
||||
public void quickSort (int[] nums, int low, int high) {
|
||||
|
||||
if (low < hight) {
|
||||
int index = partition(nums,low,hight);
|
||||
if (low < high) {
|
||||
int index = partition(nums,low,high);
|
||||
quickSort(nums,low,index-1);
|
||||
quickSort(nums,index+1,hight);
|
||||
quickSort(nums,index+1,high);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public int partition (int[] nums, int low, int hight) {
|
||||
public int partition (int[] nums, int low, int high) {
|
||||
|
||||
int pivot = nums[low];
|
||||
int start = low;
|
||||
|
||||
while (low < hight) {
|
||||
while (low < hight && nums[hight] >= pivot) hight--;
|
||||
while (low < hight && nums[low] <= pivot) low++;
|
||||
if (low >= hight) break;
|
||||
swap(nums, low, hight);
|
||||
while (low < high) {
|
||||
while (low < high && nums[high] >= pivot) high--;
|
||||
while (low < high && nums[low] <= pivot) low++;
|
||||
if (low >= high) break;
|
||||
swap(nums, low, high);
|
||||
}
|
||||
//基准值归位
|
||||
swap(nums,start,low);
|
||||
@@ -175,29 +177,29 @@ class Solution {
|
||||
stack.push(0);
|
||||
while (!stack.isEmpty()) {
|
||||
int low = stack.pop();
|
||||
int hight = stack.pop();
|
||||
int high = stack.pop();
|
||||
|
||||
if (low < hight) {
|
||||
int index = partition(nums, low, hight);
|
||||
if (low < high) {
|
||||
int index = partition(nums, low, high);
|
||||
stack.push(index - 1);
|
||||
stack.push(low);
|
||||
stack.push(hight);
|
||||
stack.push(high);
|
||||
stack.push(index + 1);
|
||||
}
|
||||
}
|
||||
return nums;
|
||||
}
|
||||
|
||||
public int partition (int[] nums, int low, int hight) {
|
||||
public int partition (int[] nums, int low, int high) {
|
||||
|
||||
int pivot = nums[low];
|
||||
int start = low;
|
||||
while (low < hight) {
|
||||
while (low < high) {
|
||||
|
||||
while (low < hight && nums[hight] >= pivot) hight--;
|
||||
while (low < hight && nums[low] <= pivot) low++;
|
||||
if (low >= hight) break;
|
||||
swap(nums, low, hight);
|
||||
while (low < high && nums[high] >= pivot) high--;
|
||||
while (low < high && nums[low] <= pivot) low++;
|
||||
if (low >= high) break;
|
||||
swap(nums, low, high);
|
||||
}
|
||||
swap(nums,start,low);
|
||||
return low;
|
||||
@@ -226,13 +228,13 @@ class Solution {
|
||||
所以我们可以加上这几行代码实现三数取中法。
|
||||
|
||||
```java
|
||||
int mid = low + ((hight-low) >> 1);
|
||||
if (nums[low] > nums[hight]) swap(nums,low,hight);
|
||||
if (nums[mid] > nums[hight]) swap(nums,mid,hight);
|
||||
int mid = low + ((high-low) >> 1);
|
||||
if (nums[low] > nums[high]) swap(nums,low,high);
|
||||
if (nums[mid] > nums[high]) swap(nums,mid,high);
|
||||
if (nums[mid] > nums[low]) swap(nums,mid,low);
|
||||
```
|
||||
|
||||
其含义就是让我们将中间元素放到 nums[low] 位置做为基准值,最大值放到 nums[hight],最小值放到 nums[mid],即 [4,2,3] 经过上面代码处理后,则变成了 [3,2,4].此时我们选取 3 做为基准值,这样也就避免掉了选取最大或最小值做为基准值的情况。
|
||||
其含义就是让我们将中间元素放到 nums[low] 位置做为基准值,最大值放到 nums[high],最小值放到 nums[mid],即 [4,2,3] 经过上面代码处理后,则变成了 [3,2,4].此时我们选取 3 做为基准值,这样也就避免掉了选取最大或最小值做为基准值的情况。
|
||||
|
||||
**三数取中法**
|
||||
|
||||
@@ -242,28 +244,28 @@ class Solution {
|
||||
quickSort(nums,0,nums.length-1);
|
||||
return nums;
|
||||
}
|
||||
public void quickSort (int[] nums, int low, int hight) {
|
||||
if (low < hight) {
|
||||
int index = partition(nums,low,hight);
|
||||
public void quickSort (int[] nums, int low, int high) {
|
||||
if (low < high) {
|
||||
int index = partition(nums,low,high);
|
||||
quickSort(nums,low,index-1);
|
||||
quickSort(nums,index+1,hight);
|
||||
quickSort(nums,index+1,high);
|
||||
}
|
||||
}
|
||||
|
||||
public int partition (int[] nums, int low, int hight) {
|
||||
public int partition (int[] nums, int low, int high) {
|
||||
//三数取中,大家也可以使用其他方法
|
||||
int mid = low + ((hight-low) >> 1);
|
||||
if (nums[low] > nums[hight]) swap(nums,low,hight);
|
||||
if (nums[mid] > nums[hight]) swap(nums,mid,hight);
|
||||
int mid = low + ((high-low) >> 1);
|
||||
if (nums[low] > nums[high]) swap(nums,low,high);
|
||||
if (nums[mid] > nums[high]) swap(nums,mid,high);
|
||||
if (nums[mid] > nums[low]) swap(nums,mid,low);
|
||||
//下面和之前一样,仅仅是多了上面几行代码
|
||||
int pivot = nums[low];
|
||||
int start = low;
|
||||
while (low < hight) {
|
||||
while (low < hight && nums[hight] >= pivot) hight--;
|
||||
while (low < hight && nums[low] <= pivot) low++;
|
||||
if (low >= hight) break;
|
||||
swap(nums, low, hight);
|
||||
while (low < high) {
|
||||
while (low < high && nums[high] >= pivot) high--;
|
||||
while (low < high && nums[low] <= pivot) low++;
|
||||
if (low >= high) break;
|
||||
swap(nums, low, high);
|
||||
}
|
||||
swap(nums,start,low);
|
||||
return low;
|
||||
@@ -291,38 +293,38 @@ class Solution {
|
||||
return nums;
|
||||
}
|
||||
|
||||
public void quickSort (int[] nums, int low, int hight) {
|
||||
public void quickSort (int[] nums, int low, int high) {
|
||||
|
||||
if (hight - low <= INSERTION_SORT_MAX_LENGTH) {
|
||||
insertSort(nums,low,hight);
|
||||
if (high - low <= INSERTION_SORT_MAX_LENGTH) {
|
||||
insertSort(nums,low,high);
|
||||
return;
|
||||
}
|
||||
int index = partition(nums,low,hight);
|
||||
int index = partition(nums,low,high);
|
||||
quickSort(nums,low,index-1);
|
||||
quickSort(nums,index+1,hight);
|
||||
quickSort(nums,index+1,high);
|
||||
}
|
||||
|
||||
public int partition (int[] nums, int low, int hight) {
|
||||
public int partition (int[] nums, int low, int high) {
|
||||
//三数取中,大家也可以使用其他方法
|
||||
int mid = low + ((hight-low) >> 1);
|
||||
if (nums[low] > nums[hight]) swap(nums,low,hight);
|
||||
if (nums[mid] > nums[hight]) swap(nums,mid,hight);
|
||||
int mid = low + ((high-low) >> 1);
|
||||
if (nums[low] > nums[high]) swap(nums,low,high);
|
||||
if (nums[mid] > nums[high]) swap(nums,mid,high);
|
||||
if (nums[mid] > nums[low]) swap(nums,mid,low);
|
||||
int pivot = nums[low];
|
||||
int start = low;
|
||||
while (low < hight) {
|
||||
while (low < hight && nums[hight] >= pivot) hight--;
|
||||
while (low < hight && nums[low] <= pivot) low++;
|
||||
if (low >= hight) break;
|
||||
swap(nums, low, hight);
|
||||
while (low < high) {
|
||||
while (low < high && nums[high] >= pivot) high--;
|
||||
while (low < high && nums[low] <= pivot) low++;
|
||||
if (low >= high) break;
|
||||
swap(nums, low, high);
|
||||
}
|
||||
swap(nums,start,low);
|
||||
return low;
|
||||
}
|
||||
|
||||
public void insertSort (int[] nums, int low, int hight) {
|
||||
public void insertSort (int[] nums, int low, int high) {
|
||||
|
||||
for (int i = low+1; i <= hight; ++i) {
|
||||
for (int i = low+1; i <= high; ++i) {
|
||||
int temp = nums[i];
|
||||
int j;
|
||||
for (j = i-1; j >= 0; --j) {
|
||||
@@ -366,6 +368,8 @@ class Solution {
|
||||
|
||||
**三数取中+三向切分+插入排序**
|
||||
|
||||
Java Code:
|
||||
|
||||
```java
|
||||
class Solution {
|
||||
private static final int INSERTION_SORT_MAX_LENGTH = 7;
|
||||
@@ -374,19 +378,19 @@ class Solution {
|
||||
return nums;
|
||||
|
||||
}
|
||||
public void quickSort(int nums[], int low, int hight) {
|
||||
public void quickSort(int nums[], int low, int high) {
|
||||
//插入排序
|
||||
if (hight - low <= INSERTION_SORT_MAX_LENGTH) {
|
||||
insertSort(nums,low,hight);
|
||||
if (high - low <= INSERTION_SORT_MAX_LENGTH) {
|
||||
insertSort(nums,low,high);
|
||||
return;
|
||||
}
|
||||
//三数取中
|
||||
int mid = low + ((hight-low) >> 1);
|
||||
if (nums[low] > nums[hight]) swap(nums,low,hight);
|
||||
if (nums[mid] > nums[hight]) swap(nums,mid,hight);
|
||||
int mid = low + ((high-low) >> 1);
|
||||
if (nums[low] > nums[high]) swap(nums,low,high);
|
||||
if (nums[mid] > nums[high]) swap(nums,mid,high);
|
||||
if (nums[mid] > nums[low]) swap(nums,mid,low);
|
||||
//三向切分
|
||||
int left = low, i = low + 1, right = hight;
|
||||
int left = low, i = low + 1, right = high;
|
||||
int pvoit = nums[low];
|
||||
while (i <= right) {
|
||||
if (pvoit < nums[i]) {
|
||||
@@ -401,11 +405,11 @@ class Solution {
|
||||
}
|
||||
}
|
||||
quickSort(nums,low,left-1);
|
||||
quickSort(nums,right+1,hight);
|
||||
quickSort(nums,right+1,high);
|
||||
}
|
||||
public void insertSort (int[] nums, int low, int hight) {
|
||||
public void insertSort (int[] nums, int low, int high) {
|
||||
|
||||
for (int i = low+1; i <= hight; ++i) {
|
||||
for (int i = low+1; i <= high; ++i) {
|
||||
int temp = nums[i];
|
||||
int j;
|
||||
for (j = i-1; j >= 0; --j) {
|
||||
@@ -426,5 +430,65 @@ class Solution {
|
||||
}
|
||||
```
|
||||
|
||||
Python Code:
|
||||
|
||||
```python
|
||||
from typing import List
|
||||
class Solution:
|
||||
INSERTION_SORT_MAX_LENGTH = 7
|
||||
def sortArray(self, nums: List[int])->List[int]:
|
||||
self.quickSort(nums, 0, len(nums) - 1)
|
||||
return nums
|
||||
|
||||
def quickSort(self, nums: List[int], low: int, high: int):
|
||||
# 插入排序
|
||||
if high - low <= self.INSERTION_SORT_MAX_LENGTH:
|
||||
self.insertSort(nums, low, high)
|
||||
return
|
||||
# 三数取中
|
||||
mid = low + ((high - low) >> 1)
|
||||
if nums[low] > nums[high]:
|
||||
self.swap(nums, low, high)
|
||||
if nums[mid] > nums[high]:
|
||||
self.swap(nums, mid, high)
|
||||
if nums[mid] > nums[low]:
|
||||
self. swap(nums, mid, low)
|
||||
# 三向切分
|
||||
left = low
|
||||
i = low + 1
|
||||
right = high
|
||||
pivot = nums[low]
|
||||
while i <= right:
|
||||
if pivot < nums[i]:
|
||||
self.swap(nums, i, right)
|
||||
right -= 1
|
||||
elif pivot == nums[i]:
|
||||
i += 1
|
||||
else:
|
||||
self.swap(nums, left, i)
|
||||
left += 1
|
||||
i += 1
|
||||
self.quickSort(nums, low, left - 1)
|
||||
self.quickSort(nums, right + 1, high)
|
||||
|
||||
def insertSort(self, nums: List[int], low: int, high: int):
|
||||
for i in range(low + 1, high + 1):
|
||||
temp = nums[i]
|
||||
j = i - 1
|
||||
while j >= 0:
|
||||
if temp < nums[j]:
|
||||
nums[j + 1] = nums[j]
|
||||
j -= 1
|
||||
continue
|
||||
break
|
||||
nums[j + 1] = temp
|
||||
|
||||
def swap(self, nums: List[int], i: int, j: int):
|
||||
temp = nums[i]
|
||||
nums[i] = nums[j]
|
||||
nums[j] = temp
|
||||
```
|
||||
|
||||
|
||||
好啦,一些常用的优化方法都整理出来啦,还有一些其他的优化算法九数取中,优化递归操作等就不在这里进行描述啦,感兴趣的可以自己看一下。好啦,这期的文章就到这里啦,我们下期见,拜了个拜。
|
||||
|
||||
|
||||
Reference in New Issue
Block a user