冒泡排序、插值法排序、二分法排序和快速排序的个人理解

     排序的各种算法,没有任何计算机语言基础的我,是在刚开始接触javascript就有了解过的。当时听得我糊里糊涂,心里千万个草泥马在奔腾,怎么javascript这么难,算法又是什么鬼东西呀。后来慢慢接触javascript后又看了两三次有关排序算法的视频,看懂之后我的感慨就是:原来计算机是这么笨的,所有数值都要一个个来比较才知道它的大小。

    我也由于各种懒癌,各种综合症博客一直都没有写。这个排序的算法让我觉得挺有意思的,也花了不少的时间在上面,所以就记录一下吧。


首先是冒泡排序:

我就只写javascript的部分了,其余的请自动在编译器或者脑子里添加。

 1 <script type="text/javascript">
 2     /*个人理解:冒泡算法的思路就是,
 3     *在原数组上,从arr[0]开始,
 4     *拿arr[0]与arr[1]、arr[2]...arr[arr.length-1]进行比较;
 5     *如果arr[0]>arr[n],则两者交换位置(这里是升序排序,降序则将大于号改为小于号),此时,arr[0]的值已经更改了
 6     *当arr[0]与arr中的所有数比较完成后,即求出了数组中最小的值,并且将其排在了第一位。
 7     *接着到arr[1]与arr[2]...arr[arr.length-1]的数进行比较,完成后arr[1]就是余下的数中最小的数(除了arr[0])
 8     *依次到arr[2]...arr[arr.length-2]分别与后面的数进行比较。完成后就得到了一个升序的数组了。
 9     *冒泡的意思就是,先求出最小的把它放在第一位,然后是倒数第二小的把它放在第二位,依次排序,就像泡泡一个个往上 冒起一样。*/
10     var Arr = [12,5,37,42,64,41,2,14,6,22];
11          function babblingSort(arr){//封装一个函数,传入arr
12             var len = arr.length;
13             for(var i=0;i<len;i++){
14                 for(var j=i+1;j<len;j++){//想想这里为什么是j=i+1???
15                     if(arr[i]>arr[j]){
16                         var temp = arr[i];//另外建一个变量用来存储arr[i]以便进行数值交换
17                         arr[i] = arr[j];
18                         arr[j] = temp;
19                     }
20                 }
21             }
22             for(var i=0;i<len;i++){
23                 document.write(arr[i]+",");//也可以直接打印arr.
24             }
25         };
26         babblingSort(Arr);//调用函数
27     </script>

插值法排序:

 1 <script type="text/javascript">
 2         //插值法排序
 3         /*个人理解:
 4         *另外建一个新数组
 5         *令新数组的第一个值等于原数组的第一个值
 6         *然后原数组从第二个值开始(第一个已经放进了新数组),将其余新数组的每一项进行比较,
 7         *将小于放前面,大的放后面(看例子可了解具体执行过程)*/
 8 
 9         var Arr = [12,5,37,42,64,41,2,14,6,22];
10         function insetSort(arr){
11              var arrSort = [];   //新建一个空数组
12              arrSort[0] = arr[0];   //令新数组首项等于原数组首项      
13              var len = arr.length;
14              var flag;       
15              for(var i=1;i<len;i++){
16                  flag = 0;     
17                  var sortLen = arrSort.length;
18                  for(var j=0;j<sortLen;j++){
19                  //从左到右遍历新数组中的数,如果出现大于arr[i]的值,则把arr[i]存放于该数值的位置,并跳出循环。
20                     if(arr[i]<arrSort[j]){
21                             arrSort.splice(j,0,arr[i]);  
22                           flag = 1;
23                           break;
24                      }
25                  }
26                  if(flag==0){//如果该数值大于arrSort中的任意数值,则会存放到最后。
27                      arrSort.push(arr[i]);  
28                  }
29              
30              }
31              len = arrSort.length;
32              for(var i=0;i<len;i++){
33                  document.write(arrSort[i]+",");
34              }
35         }
36         insetSort(Arr);
37     </script>

二分法排序:

 1 <script type="text/javascript">
 2 
 3         // 类似于插值法排序,只是将比较的方式改变了,如果理解了前两种排序方法二分法排序也很容易理解的,这里不做详解了
 4         var Arr = [12,5,37,42,64,41,2,14,6,22];
 5         function halfSort(arr){
 6             var nArr =[];
 7             nArr[0] = arr[0];
 8             var len = arr.length;
 9             var left = 0;
10             var right = 0;
11             var point = 0;
12             
13             for(var i=1;i<len;i++){
14                 left = 0;
15                 var nlen = nArr.length;
16                 right = nlen;
17                 for(var j=0;j<nlen;j++){   //这里的j仅代表循环的次数
18                     point = Math.floor((left+right)/2);    //Math.ceil(),Math.floor的区分
19                     if(nArr[point]<arr[i]){  //若该值为true,则arr[i]应排在新数组中间右边的位置
20                         left = point+1;  //再依次加一,即向右逐个比较数组的每个数。这里貌似可以改良。我水平有限不懂
21                     }else{
22                         right = point;//arr[i]与nArr[point]已经作过比较,所以arr[i]只需与nArr[point]前面的point个数比
23                     }
24                     if (left==right) {
25                         nArr.splice(left,0,arr[i]);
26                         break;
27                     }
28                 }
29 
30             }
31             var nlen = nArr.length;
32             console.log(nArr[7]);
33             for(var i=0;i<nlen;i++){
34                 document.write(nArr[i]+",");
35             }
36         }
37         halfSort(Arr);
38     </script>

快速排序:

 1         /*     
 2         *首先要了解concat()函数和函数的递归操作
 3         *1.找一个基准点
 4         *2.建立两个数组,分别存储左边和右边的数组
 5         *3.利用递归,进行拆分,用concat()函数将其拼接起来
 6             */
 7         function quickSort(arr){
 8 
 9             if(arr.length<=1){
10                 return arr;//想想这里为什么要返回arr呢?
11             }
12             
13             var num = Math.floor(arr.length/2);  
14 
15             var numValue = arr.splice(num,1);  //求出数组索引值的中间值,这个例子中的第一个numValue是:41
16             var left = [];
17             var right = [];
18 
19             for(var i=0;i<arr.length;i++){
20                 var j = i;
21                 if(arr[i]<numValue){   //把小于numValue的数存到左边
22                     left.push(arr[i]);
23                 }
24                 else{        //把大于numValue的数存到右边
25                     right.push(arr[i]);
26                 }
27             }
28             
29             /*document.write('L:'+left+"<br>");   //可以试着打印left值和right值,查看数组的具体拆分,
30             *document.write('R:'+right+"<br><br>");
31             *下面数字表示执行的顺序
32             *     ①  L:12,5,37,2,14,6,22,40                   R:42,64
33             *          
34             *    ② L:12,5,2,6              R:37,22,40          ⑧ L:42 R:空
35             *    
36             *   ③ L:空    R:12,5,6        ⑥ L:空   R37,40     
37             *   
38             *         ④ L:空    R:12,6             ⑦  L:37  R:空 
39             *          
40             *                  ⑤ L:空  R12   
41             * 以上的每个被拆分的数组都会传入quickSort() 函数,当值为空或者只有一个数的时候
42             * 就返回了空值或那个数值,结束了当前分支的循环(循环使用quickSort()函数)。
43             * 
44             */
45 
46             return quickSort(left).concat([numValue],quickSort(right));//这是总的返回值
47         }
               var Arr = [12,5,37,42,64,41,2,14,6,22];
48             var result = quickSort(Arr); 
49 document.write(result);

以上是个人对四种排序方法的理解。在学习的过程中,算法总让我感到困难而又感觉挺有意思的,特别是用枚举法解决数学问题的时候,让我有点惊喜的感觉(我只是个小菜鸟,大家有啥看法可以随便说)。没有计算机语言基础的我,在之前犹豫了一段时间后还是选择了码农这条路。到现在也差不多自学了3、4个月了,期间还算努力,HTML 、CSS、javascript、jQuery基本都算入门了。现在就快得开始找工作了,心里各种担忧,各种“万一”、“怎么办”。早晚还是得面对的。

 

posted @ 2017-05-26 18:02  Nicholasyi  阅读(1728)  评论(0编辑  收藏  举报