代码主要分三块,快排,画图和调度。
快排不说了。画图方法arrange接收3个参数:当前处理的数组,在原始数组中的最低位和最高位;这样设计主要是为了适应以递归方式实现快排时,每进行一次迭代就要在相应位置画出图形。
调度方法采用闭包的原理,在快排算法执行时,保存每次需要执行的画图任务。然后在最终暴露的方法中,使用自定义的next方法开始执行。
整个的过程就是先执行一遍快排,在执行过程中储存每次迭代时的画图任务,最后依次执行这些画图任务。
1 <!DOCTYPE html> 2 <html lang="en"> 3 <head> 4 <meta charset="UTF-8"> 5 <title>quickSort</title> 6 <style> 7 .wrap{display: flex;width: 600px;height:500px;background-color: #eee;align-items:flex-end;justify-content:space-around;} 8 .bar{ 9 color: #fff; 10 text-align: center; 11 background-color: #46b; 12 } 13 </style> 14 15 </head> 16 <body> 17 <div class="wrap"></div> 18 <script type="text/javascript"> 19 (function(window){ 20 var wrap = document.getElementsByClassName('wrap')[0]; 21 var bar_width; 22 var rate 23 var man 24 25 /*快排方法*/ 26 function quickSort(arr,low,high){ 27 if(arr instanceof Array){ 28 var len = arr.length; 29 if(len>1){ 30 var left=[],right=[]; 31 var midindex = Math.floor(len/2); 32 var mid = arr.splice(midindex,1); 33 for(var i=0;i<len-1;i++){ 34 var item = arr[i]; 35 if(item>mid)right.push(item); 36 else left.push(item); 37 } 38 man.addtask(arrange(left.concat(mid,right),low,high))/*保存画图任务*/ 39 return quickSort(left,low,low+left.length).concat(mid,quickSort(right,high-right.length,high)) 40 }else return arr; 41 }else return []; 42 } 43 44 /*画图方法*/ 45 function arrange(dataArray,low,high){ 46 function _arrange(){ 47 var bars=[] 48 for(var i=0,len=dataArray.length;i<len;i++){ 49 var bar = document.createElement('div') 50 bar.setAttribute('class','bar') 51 var h = Math.floor(dataArray[i]*rate) 52 bar.style.height= h+'px' 53 bar.style.width= bar_width+'px' 54 bar.innerHTML=dataArray[i]+''; 55 bars[i]=bar 56 } 57 for(var i=low,j=0;i<high;i++,j++){ 58 var bar = bars[j]; 59 var target = document.getElementsByClassName('bar')[i]; 60 wrap.replaceChild(bar,target); 61 } 62 } 63 return _arrange;/*使用闭包保存输入参数*/ 64 } 65 66 /*调度方法*/ 67 function manage(dataArray){ 68 this.tasks = [] 69 } 70 manage.prototype.next=function(){ 71 var fn = this.tasks.shift() 72 var self = this; 73 setTimeout(function(){ 74 fn&&fn(); 75 self.next() 76 },900) 77 78 } 79 manage.prototype.addtask=function(task){ 80 this.tasks.push(task) 81 } 82 83 /*初始化方法*/ 84 function init(dataArray){ 85 bar_width = Math.floor(getComputedStyle(wrap).width.split('px')[0]*1/(dataArray.length+1)) 86 var big= getbiggest(dataArray); 87 var base = getComputedStyle(wrap).height.split('px')[0]*1 88 rate = base/big; 89 man = new manage() 90 for(var i=0,len=dataArray.length;i<len;i++){ 91 var bar = document.createElement('div') 92 bar.setAttribute('class','bar') 93 bar.style.width= bar_width+'px' 94 wrap.appendChild(bar); 95 } 96 } 97 98 /*工具方法*/ 99 function getbiggest(arr){ 100 var biggest=arr[0]; 101 for(var i=0,len=arr.length;i<len;i++){ 102 biggest=biggest<arr[i]?arr[i]:biggest; 103 } 104 return biggest; 105 } 106 107 /*暴露方法*/ 108 window.quickSort_show=function(dataArray){ 109 init(dataArray); 110 quickSort(dataArray,0,dataArray.length); 111 man.next() 112 } 113 })(window) 114 115 var dataArray = [85,24,53,45,63,31,17,96,50,33,59,73,26,66,10,56,77,34,23,76,44,32,96]; 116 quickSort_show(dataArray) 117 </script> 118 </body> 119 </html>