zoukankan      html  css  js  c++  java
  • 分治算法-快速,归并

    快速排序和归并排序是典型的分治算法。

     code:快速排序

    <!doctype html>
    <html>
    <head>
      <meta charset="utf-8">
      <title>快速,归并</title>
    
    </head>
    <body>
     <div id="log"></div>
    
      <script>
      var data = [],num = 1000;
        for(var i = 0;i<num;i++){
            data.push(Math.floor(Math.random()*num))
        }
        console.time('quick2')
        var newData = quick2(data);
        console.timeEnd('quick2')
        data = [];
        for(var i = 0;i<num;i++){
            data.push(Math.floor(Math.random()*num))
        }
        console.time('quickSort')
        var newData = quickSort(data);
        console.timeEnd('quickSort')
        function quick2(data,base){
            if(data.length < 2 ){return data;}
            var d1=[],d2=[],base = base||data.shift();
            for(var j = 0 ;j < data.length;j++){
                if(data[j]>base){
                    d1.push(data[j]);
                }else{
                    d2.push(data[j]);
                }
            }
            return [].concat(quick2(d1)).concat(base).concat(quick2(d2));
        }
        function quickSort(array) {
            function sort(prev, numsize) {
                var nonius = prev;
                var j = numsize - 1;
                var flag = array[prev];
                if ((numsize - prev) > 1) {
                    while (nonius < j) {
                        for (; nonius < j; j--) {
                            if (array[j] < flag) {
                                array[nonius++] = array[j];  //a[i] = a[j]; i += 1;
                                break;
                            };
                        }
                        for (; nonius < j; nonius++) {
                            if (array[nonius] > flag) {
                                array[j--] = array[nonius];
                                break;
                            }
                        }
                    }
                    array[nonius] = flag;
                    sort(prev, nonius);
                    sort(nonius + 1, numsize);
                }
            }
            sort(0, array.length);
            return array;
        }
      </script>
    </body>
    </html>

    quick2 是我自己根据分治的意思写的,写完之后去网上查,发现网上的都是挖坑算的,quickSort是网上找的,一开始运行很慢,后来改了处关键地方就快了,

    计较结果上看,quickSort优势还是很明显的,可能是我用临时变量太多引起的。

     可能利用了cancat的便利性(据说数组的concat方法比直接for循环push要慢)。

    接下来是归并,我自己尝试写的

    function merge(data){
            if(data.length === 1){
                return data;
            }
            var y = data.length%2; 
            var s = y?(data.length-1)/2:data.length/2;
            var d1 = merge(data.slice(0,s));
            var d2 = merge(data.slice(s,data.length));
            var i=0; var j=0; var d3=[];
            while(i<d1.length || j<d2.length){
                if(!d1[i]){
                    d3.push(d2[j++]);
                }else{
                    if(!d2[j]){
                        d3.push(d1[i++]);
                    }else{
                        if(d2[j]<d1[i]){
                            d3.push(d2[j++]);
                        }else{
                           d3.push(d1[i++]);
                        }
                    }
                }
            }
            return d3;
        }

    但是明显比快速排序慢一些,我去百度上找了一段

        function merge1(left, right) {
            var result = [];
            while (left.length > 0 && right.length > 0) {
                if (left[0] < right[0]) {
                    /*shift()方法用于把数组的第一个元素从其中删除,并返回第一个元素的值。*/
                    result.push(left.shift());
                } else {
                    result.push(right.shift());
                }
            }
            return result.concat(left).concat(right);
        }
        function mergeSort(items) {
            if (items.length == 1) {
                return items;
            }
            var middle = Math.floor(items.length / 2),
            left = items.slice(0, middle),
            right = items.slice(middle);
            return merge1(mergeSort(left), mergeSort(right));
        }

    明显人家的归并这一步干净利索,让我汗颜啊

    赶紧copy过来。

    尴尬的是竟然变慢了三分之一。。。

    比快速排序慢的原因应该还是临时变量太多

    练习:

    输入

    首先是解析

    <div id='wis'></div>
    <script src="jquery.js"></script>
    <script>
    function decompress(str){
        var docompressed = [[],[],[],[],[],[],[],[],[],[],[],[],[],[],[],[]],ary = str.split(''),it = 0;
        function de(y,x,size){
        var head = ary[it++];
        console.log(it + ' & ' + head + '->y: ' + y + ', x: ' + x + ', s: ' + size);
            if(head == 'b' || head == 'w'){
                for(var i = 0;i<size;i++){
                    for(var j = 0;j<size;j++){
                        docompressed[i+y][j+x] = head;
                    }
                }
                console.log(docompressed);
            }else{
            var half = size/2;
                de(y,x,half);
                de(y,x+half,half);
                de(y+ half,x,half);
                de(y + half,x +half,half);
            }
        }
        de(0,0,16);
        return docompressed;
    }
    var data = decompress('xxwwwbxwxwbbbwwxxxwwbbbwwwwbb'),
    width = $(window).width();
    for( var m = 0; m< data.length;m++){
        var d = $('<div style="100%;float:left">');
        for(var n=0;n<data[m].length;n++){
            d.append($('<div >').css('width','20px').css('height','20px').css('background-color',data[m][n] === 'w'?'#c1c1c1':'black').css('float','left'));
        }
        $(wis).append(d);
    }
    </script>

     然后是反转数组,再次压缩。。

    还是学习他的第二种方案吧

    完整的代码如下:

    <div id='wis'></div>
    <script src="jquery.js"></script>
    <script>
    function decompress(str){
        var docompressed = [[],[],[],[],[],[],[],[],[],[],[],[],[],[],[],[]],ary = str.split(''),it = 0;
        function de(y,x,size){
        var head = ary[it++];
        console.log(it + ' & ' + head + '->y: ' + y + ', x: ' + x + ', s: ' + size);
            if(head == 'b' || head == 'w'){
                for(var i = 0;i<size;i++){
                    for(var j = 0;j<size;j++){
                        docompressed[i+y][j+x] = head;
                    }
                }
                console.log(docompressed);
            }else{
            var half = size/2;
                de(y,x,half);
                de(y,x+half,half);
                de(y+ half,x,half);
                de(y + half,x +half,half);
            }
        }
        de(0,0,16);
        return docompressed;
    }
    function recerse(str){
        var ary = str.split(''),it=0;
        function op(){
            var head = ary[it++];
            if(head == 'b' || head == 'w'){
                return head;
            }
            var leftUp = op(it);
            var rightUp = op(it);
            var leftDown = op(it);
            var rightDown = op(it);
            return 'x' + leftDown + rightDown + leftUp + rightUp; 
        }
        return op();
    }
    function show(data){
        for( var m = 0; m< data.length;m++){
            var d = $('<div style="100%;float:left">');
            for(var n=0;n<data[m].length;n++){
                d.append($('<div >').css('width','20px').css('height','20px').css('background-color',data[m][n] === 'w'?'#c1c1c1':'black').css('float','left'));
            }
            $(wis).append(d);
        }
        $(wis).append($('<div style="100%;float:left;border-bottom:1px solid red;">'));
    }
    var str = 'xxwwwbxwxwbbbwwxxxwwbbbwwwwbb';
    var data = decompress(str);
    show(data);
    var data2 = decompress(recerse(str));
    show(data2);
    </script>
  • 相关阅读:
    撕衣服
    寒假作业1编程总结。
    C Traps and Pitfallss
    《彻底搞定C指针》文档整理
    C语言中内存分配 (转)
    ASCII
    ipad
    tour
    Diet
    第7章 输入与输出
  • 原文地址:https://www.cnblogs.com/poorpeople/p/7199965.html
Copyright © 2011-2022 走看看