Merge pull request #6 from wangzheng0822/master

合并上游代码
This commit is contained in:
leo 2018-10-17 12:20:20 +08:00 committed by GitHub
commit 41c016180e
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
14 changed files with 532 additions and 86 deletions

View File

@ -49,13 +49,11 @@ public class Sorts {
// 选择排序a表示数组n表示数组大小
public static void selectionSort(int[] a, int n) {
if (n <= 1) return;
for (int i = 0; i < n; ++i) {
for (int i = 0; i < n - 1; ++i) {
// 查找最小值
int minIndex = i;
int minValue = a[i];
for (int j = i; j < n; ++j) {
if (a[j] < minValue) {
minValue = a[j];
for (int j = i + 1; j < n; ++j) {
if (a[j] < a[minIndex]) {
minIndex = j;
}
}

View File

@ -0,0 +1,100 @@
package sorts;
/**
* 向下冒泡算法 或许比冒泡更易懂的排序算法
* 希尔排序
*
* Author: wliu
*/
public class SortsAddOn {
public static void main(String[] args) {
int[] arr = {3, 2, 6, 4, 5, 1, 9, 20, 13, 16};
// bubbleDownSort(arr);
shellSort(arr);
print(arr);
}
/**
* 向下冒泡可能比冒泡更易懂
*
* 算法概要
* 从0开始用这个元素去跟后面的所有元素比较如果发现这个元素大于后面的某个元素则交换
* 3 2 6 4 5 1
* 第一趟是从 index=0 也就是 3 开始跟index=1及其后面的数字比较
* 3 大于 2交换变为 2 3 6 4 5 1此时index=0的位置变为了2
* 接下来将用2跟index=2比较
* 2 不大于 6 不交换
* 2 不大于 4 不交换
* 2 不大于 5 不交换
* 2 大于 1交换变为 1 3 6 4 5 2第一趟排序完成
*
* 第二趟是从 index=1 也就是 3开始跟index=2及其后面的数字比较
* 3 不大于 6 不交换
* 3 不大于 4 不交换
* 3 不大于 5 不交换
* 3 大于 2交换变为 1 2 6 4 5 3第二趟排序完成
*
* 第三趟是从 index=2 也就是 6开始跟index=3及其后面的数字比较
* 6 大于 4交换变为 1 2 4 6 5 3, 此时 index = 2 的位置变为了4
* 接下来将用4跟index=4比较
* 4 不大于 5 不交换
* 4 大于 3交换变为 1 2 3 6 5 4第三趟排序完成
*
* 第四趟是从 index=3 也就是 6开始跟index=4及其后面的数字比较
* 6 大于 5交换变为 1 2 3 5 6 4, 此时 index = 3 的位置变为了5
* 接下来将用5跟index=5比较
* 5 大于 4交换变为 1 2 3 4 6 5, 第四趟排序完成
*
* 第五趟是从 index=4 也就是 6开始跟index=5及其后面的数字比较
* 6 大于 5交换变为 1 2 3 4 5 6, 此时 index = 4 的位置变为了5
* 接下来将用5跟index=6比较
* index = 6 已经不满足 index < length 的条件整个排序完成
*/
private static void bubbleDownSort(int[] arr) {
int len = arr.length;
if (len == 1) return;
for (int i = 0; i < len; i++) {
for (int j = i + 1; j < len; j++) {
if (arr[i] > arr[j]) {
int tmp = arr[i];
arr[i] = arr[j];
arr[j] = tmp;
}
}
}
}
private static void shellSort(int[] arr) {
int len = arr.length;
if (len == 1) return;
int step = len / 2;
while (step >= 1) {
for (int i = step; i < len; i++) {
int value = arr[i];
int j = i - step;
for (; j >= 0; j -= step) {
if (value < arr[j]) {
arr[j+step] = arr[j];
} else {
break;
}
}
arr[j+step] = value;
}
step = step / 2;
}
}
private static void print(int[] arr) {
System.out.println("Print array:");
for (int x : arr) {
System.out.print(x + "\t");
}
System.out.println("");
}
}

View File

@ -0,0 +1,60 @@
package sorts;
/**
* Created by wangzheng on 2018/10/16.
*/
public class MergeSort {
// 归并排序算法, a是数组n表示数组大小
public static void mergeSort(int[] a, int n) {
mergeSortInternally(a, 0, n-1);
}
// 递归调用函数
private static void mergeSortInternally(int[] a, int p, int r) {
// 递归终止条件
if (p >= r) return;
// 取p到r之间的中间位置q
int q = (p+r)/2;
// 分治递归
mergeSortInternally(a, p, q);
mergeSortInternally(a, q+1, r);
// 将A[p...q]和A[q+1...r]合并为A[p...r]
merge(a, p, q, r);
}
private static void merge(int[] a, int p, int q, int r) {
int i = p;
int j = q+1;
int k = 0; // 初始化变量i, j, k
int[] tmp = new int[r-p+1]; // 申请一个大小跟a[p...r]一样的临时数组
while (i<=q && j<=r) {
if (a[i] <= a[j]) {
tmp[k++] = a[i++]; // i++等于i:=i+1
} else {
tmp[k++] = a[j++];
}
}
// 判断哪个子数组中有剩余的数据
int start = i;
int end = q;
if (j <= r) {
start = j;
end = r;
}
// 将剩余的数据拷贝到临时数组tmp
while (start <= end) {
tmp[k++] = a[start++];
}
// 将tmp中的数组拷贝回a[p...r]
for (i = 0; i <= r-p; ++i) {
a[p+i] = tmp[i];
}
}
}

View File

@ -0,0 +1,41 @@
package sorts;
/**
* Created by wangzheng on 2018/10/16.
*/
public class QuickSort {
// 快速排序a是数组n表示数组的大小
public static void quickSort(int[] a, int n) {
quickSortInternally(a, 0, n-1);
}
// 快速排序递归函数p,r为下标
private static void quickSortInternally(int[] a, int p, int r) {
if (p >= r) return;
int q = partition(a, p, r); // 获取分区点
quickSortInternally(a, p, q-1);
quickSortInternally(a, q+1, r);
}
private static int partition(int[] a, int p, int r) {
int pivot = a[r];
int i = p;
for(int j = p; j < r; ++j) {
if (a[j] < pivot) {
int tmp = a[i];
a[i] = a[j];
a[j] = tmp;
++i;
}
}
int tmp = a[i];
a[i] = a[r];
a[r] = tmp;
System.out.println("i=" + i);
return i;
}
}

2
php/.gitignore vendored
View File

@ -1,2 +1,4 @@
.idea
vendor
*my*
Queue

View File

@ -28,6 +28,14 @@ function expression($str)
array_push($operStack, $arr[$i]);
break;
case '*':
$arrLen = count($operStack);
while ($operStack[$arrLen-1] === '/'){
compute($numStack, $operStack);
$arrLen--;
}
array_push($operStack, $arr[$i]);
break;
case '/':
case '(':
array_push($operStack, $arr[$i]);
@ -70,7 +78,9 @@ function compute(&$numStack, &$operStack){
case '-':
array_push($numStack, array_pop($numStack) - $num);
break;
case '(':
throw new \Exception("不匹配的(", 2);
break;
}
}
expression('-1+2-(1+2*3)');

View File

@ -0,0 +1,115 @@
<?php
/**
* User: Hkesd
* Date: 2018/10/13 11:26
* Desc:
*/
namespace Algo_09;
use Algo_06\SingleLinkedListNode;
/**
* 队列 链表实现
*
* Class QueueOnLinkedList
*/
class QueueOnLinkedList
{
/**
* 队列头节点
*
* @var SingleLinkedListNode
*/
public $head;
/**
* 队列尾节点
*
* @var null
*/
public $tail;
/**
* 队列长度
*
* @var int
*/
public $length;
/**
* QueueOnLinkedList constructor.
*/
public function __construct()
{
$this->head = new SingleLinkedListNode();
$this->tail = $this->head;
$this->length = 0;
}
/**
* 入队
*
* @param $data
*/
public function enqueue($data)
{
$newNode = new SingleLinkedListNode();
$newNode->data = $data;
$this->tail->next = $newNode;
$this->tail = $newNode;
$this->length++;
}
/**
* 出队
*
* @return SingleLinkedListNode|bool|null
*/
public function dequeue()
{
if (0 == $this->length) {
return false;
}
$node = $this->head->next;
$this->head->next = $this->head->next->next;
$this->length--;
return $node;
}
/**
* 获取队列长度
*
* @return int
*/
public function getLength()
{
return $this->length;
}
/**
* 打印队列
*/
public function printSelf()
{
if (0 == $this->length) {
echo 'empty queue' . PHP_EOL;
return;
}
echo 'head.next -> ';
$curNode = $this->head;
while ($curNode->next) {
echo $curNode->next->data . ' -> ';
$curNode = $curNode->next;
}
echo 'NULL' . PHP_EOL;
}
}

View File

@ -0,0 +1,60 @@
<?php
class LoopQueue
{
private $MaxSzie;
private $data = [];
private $head = 0;
private $tail = 0;
/**
* 初始化队列大小 最后的位置不存放数据,实际大小 = size++
*/
public function __construct($size = 10)
{
$this->MaxSzie = ++$size;
}
/**
* 队列满条件 ($this->tail+1) % $this->MaxSzie == $this->head
*/
public function enQueue($data)
{
if (($this->tail+1) % $this->MaxSzie == $this->head)
return -1;
$this->data[$this->tail] = $data;
$this->tail = (++$this->tail) % $this->MaxSzie;
}
public function deQueue()
{
if ($this->head == $this->tail)
return NULL;
$data = $this->data[$this->head];
unset($this->data[$this->head]);
$this->head = (++$this->head) % $this->MaxSzie;
return $data;
}
public function getLength()
{
return ($this->tail - $this->head + $this->MaxSzie) % $this->MaxSzie;
}
}
$queue = new LoopQueue(4);
// var_dump($queue);
$queue->enQueue(1);
$queue->enQueue(2);
$queue->enQueue(3);
$queue->enQueue(4);
// $queue->enQueue(5);
var_dump($queue->getLength());
$queue->deQueue();
$queue->deQueue();
$queue->deQueue();
$queue->deQueue();
$queue->deQueue();
var_dump($queue);

29
php/09_queue/main.php Normal file
View File

@ -0,0 +1,29 @@
<?php
/**
* User: Hkesd
* Date: 2018/10/13 11:46
* Desc:
*/
namespace Algo_09;
require_once "../vendor/autoload.php";
$queue = new QueueOnLinkedList();
$queue->enqueue(1);
$queue->enqueue(2);
$queue->enqueue(3);
$queue->enqueue(4);
$queue->enqueue(5);
$queue->printSelf();
var_dump($queue->getLength());
$queue->dequeue();
$queue->printSelf();
$queue->dequeue();
$queue->dequeue();
$queue->dequeue();
$queue->printSelf();
$queue->dequeue();
$queue->printSelf();

24
php/11_sort/Sort.php Normal file
View File

@ -0,0 +1,24 @@
<?php
function insertSort(&$arr)
{
$i = 0;
$len = count($arr);
while($i < $len){
$data = $arr[$i+1];
for ($j = $i;$j >=0 ;$j-- ){
if ($data >= $arr[$j]){
array_splice($arr, $i+1, 1);
array_splice($arr, ++$j, 0, $data);
break;
}
}
$i++;
}
}
$arr = [1,4,6,2,3,5,4];
insertSort($arr);
var_dump($arr);

View File

@ -17,4 +17,7 @@
* findMiddleNode 求链表的中间结点
#### 08_stack
* 链栈实现
* 链栈实现
#### 09_stack
* 队列链表实现

View File

@ -1,78 +0,0 @@
<?php
// 四则运算 +-*/()
function expression($str)
{
$str = str_replace(' ','',$str);
$arr = preg_split('/([\+\-\*\/\(\)])/', $str, -1, PREG_SPLIT_DELIM_CAPTURE | PREG_SPLIT_NO_EMPTY);
$numStack = []; // 存放数字
$operStack = []; // 存放运算符
$operStack[] = NULL;
for ($i = 0; $i < count($arr); $i++){
if (ord($arr[$i]) >= 48 && ord($arr[$i] <= 57)){
array_push($numStack, $arr[$i]);
continue;
}
switch ($arr[$i]){
case '+':
case '-':
$arrLen = count($operStack);
while ($operStack[$arrLen-1] === '*' || $operStack[$arrLen-1] === '/' || $operStack[$arrLen-1] === '-'){
compute($numStack, $operStack);
$arrLen--;
}
array_push($operStack, $arr[$i]);
break;
case '*':
case '/':
case '(':
array_push($operStack, $arr[$i]);
break;
case ')':
$arrLen = count($operStack);
while ($operStack[$arrLen-1] !== '('){
compute($numStack, $operStack);
$arrLen--;
}
array_pop($operStack);
break;
default:
throw new \Exception("不支持的运算符", 1);
break;
}
}
$arrLen = count($operStack);
while ($operStack[$arrLen-1] !== NULL){
compute($numStack, $operStack);
$arrLen--;
}
echo array_pop($numStack);
}
//数字栈长度减一,运算符栈长度减一
function compute(&$numStack, &$operStack){
$num = array_pop($numStack);
switch (array_pop($operStack)) {
case '*':
array_push($numStack, array_pop($numStack) * $num);
break;
case '/':
array_push($numStack, array_pop($numStack) / $num);
break;
case '+':
array_push($numStack, array_pop($numStack) + $num);
break;
case '-':
array_push($numStack, array_pop($numStack) - $num);
break;
}
}
expression('-1+2-(1+2*3)');
echo PHP_EOL;
eval('echo -1+2-(1+2*3);');

View File

@ -7,7 +7,8 @@
"psr-4": {
"Algo_06\\": "06_linkedlist/",
"Algo_07\\": "07_linkedlist/",
"Algo_08\\": "08_stack/"
"Algo_08\\": "08_stack/",
"Algo_09\\": "09_queue/"
}
}
}

View File

@ -0,0 +1,81 @@
import Foundation
///
///
/// - Parameter elements:
/// - Returns:
public func bubbleSort<T>(_ elements: [T]) ->[T] where T: Comparable {
var array = elements
guard array.count > 1 else {
return array
}
for i in 0..<array.count {
// 退
var flag = false
for j in 0..<array.count - i - 1 {
if array[j] > array[j+1] {
array.swapAt(j+1, j)
//
flag = true
}
}
if (!flag) {
break
}
}
return array
}
///
///
/// - Parameter elements:
/// - Returns:
public func insertionSort<T>(_ elements: [T]) -> [T] where T: Comparable {
var array = elements
guard array.count > 1 else {
return array
}
for i in 1..<array.count {
let value = array[i]
var j = i - 1;
//
for p in (0...j).reversed() {
j = p
if array[p] > value {
array[p+1] = array[p]
} else {
break
}
}
array[j+1] = value
}
return array
}
///
///
/// - Parameter elements:
/// - Returns:
public func selectionSort<T>(_ elements: [T]) -> [T] where T: Comparable {
var array = elements
guard array.count > 1 else {
return array
}
for i in 0..<array.count {
//
var minIndex = i
var minValue = array[i]
for j in i..<array.count {
if array[j] < minValue {
minValue = array[j]
minIndex = j
}
}
//
array.swapAt(i, minIndex)
}
return array
}