澳门永利备用网址三、删除成分,希尔和堆排序

壹、成分赋值

希尔和堆排序

 1 #我们前面学习过赋值语句,赋值语句是最简单地改变列表的方式,如 a=2 就是一种改变列表的方式。这里我们将通过编号标记某个特定位置的元素,并对该位置的元素重新赋值,如a[1]=10.例:
 2 >>> a=[1,2,3,2,1]
 3 >>> a[1]=10
 4 >>> a
 5 [1, 10, 3, 2, 1]
 6 >>> a[3]=10
 7 >>> a
 8 [1, 10, 3, 10, 1]
 9 #元素编号从0开始,1对应的是2,3对应的是也是2.
10 
11 #从上面的输出结果可以得知,我们可以根据编号对列表中某个元素重新赋值。既然可以重新赋值,是否可以赋不同类型的值呢?例:
12 >>> a[2]='hello'    
13 >>> a
14 [1, 10, 'hello', 10, 1]
15 >>> type(a[2])
16 <class 'str'>
17 >>> type(a[1])
18 <class 'int'>
19 >>> type(a)
20 <class 'list'>
21 #由上面的输出结果可以得知,可以对一个列表中的元素赋不同类型的值。比如上面的示例,列表a中既有int类型的值,也有str类型的值。
22 
23 #假如对列表赋值时使用的编号超过了列表中的最大编号,是否还可以赋值呢?
24 >>> tring=[1,2,3]
25 >>> tring[3]='hello'
26 Traceback (most recent call last):
27   File "<pyshell#34>", line 1, in <module>
28     tring[3]='hello'
29 IndexError: list assignment index out of range
30 #由上面的示例中,tring的最大编号是2,当给编号为3的元素赋值时就会出错。由此得知:不能为一个不存在的元素的位置赋值。如果一定要赋值,前面学习的序列通用操作中的乘法可以帮助我们:
31 >>> tring=[None]*5
32 >>> tring[3]='hello'
33 >>> tring
34 [None, None, None, 'hello', None]
35 #由以上输出结果可以得知,可以对初始化过的位置进行赋值
//希尔排序(插入)
Array.prototype.shellSort = function(){
  var increment = this.length;
  console.info('初始化步长:'+increment);
  var temp,j;
  do{
    increment = parseInt(increment/3)+1;
    console.info('步长变为:'+increment);
    for (var i = increment; i < this.length; i++) {
      console.info('对比 第'+i+'个元素:'+this[i]+',第'+(i-increment)+'个元素:'+
        this[i-increment]);
      if(this[i]<this[i-increment]){
        temp = this[i];
        for(j = i-increment;j>=0&&temp<this[j];j-=increment){
          console.info('赋值 第'+(j+increment)+'个元素'+this[j+increment]
            +'赋值为第'+j+'元素'+this[j]);
          this[j+increment] = this[j];
        }
        this[j+increment] = temp;
        console.info('赋值 第'+(j+increment)+'个元素'+this[j+increment]
          +'赋值为第'+i+'元素'+temp);
      }
    }
  }
  while(increment>1);
}
//堆排序
//调整函数
Array.prototype.headAdjust = function(pos, len){
  //将当前节点值进行保存
  var swap = this[pos];
  //定位到当前节点的左边的子节点
  var child = pos * 2 + 1;
  //递归,直至没有子节点为止
  while(child < len){
    //如果当前节点有右边的子节点,并且右子节点较大的场合,采用右子节点
    //和当前节点进行比较
    if(child + 1 < len && this[child] < this[child + 1]){
      child += 1;
    }
    //比较当前节点和最大的子节点,小于则进行值交换,交换后将当前节点定位
    //于子节点上
    if(this[pos] < this[child]){
      this[pos] = this[child];
      pos = child;
      child = pos * 2 + 1;
    }
    else{
      break;
    }
    this[pos] = swap;
  }
}

//构建堆
Array.prototype.buildHeap = function(){
  //从最后一个拥有子节点的节点开始,将该节点连同其子节点进行比较,
  //将最大的数交换与该节点,交换后,再依次向前节点进行相同交换处理,
  //直至构建出大顶堆(升序为大顶,降序为小顶)
  for(var i=parseInt(this.length/2); i>=0; i--){
    this.headAdjust(i, this.length);
  }
}

Array.prototype.heapSort = function(){
  //构建堆
  this.buildHeap();
  //从数列的尾部开始进行调整
  for(var i=this.length-1; i>0; i--){
    //堆顶永远是最大元素,故,将堆顶和尾部元素交换,将
    //最大元素保存于尾部,并且不参与后面的调整
    var swap = this[i];
    this[i] = this[0];
    this[0] = swap;
    //进行调整,将最大)元素调整至堆顶
    this.headAdjust(0, i);
  }
}
var a1 = [3, 1, 5, 7, 2, 4, 9, 6, 10, 8];
console.log('希尔排序before: ' + a1);
a1.shellSort();
console.log('希尔排序after: ' + a1);
var a2 = [3, 1, 5, 7, 2, 4, 9, 6, 10, 8];
console.log('堆排序before: ' + a2);
a2.heapSort();
console.log('堆排序after: ' + a2);

贰、扩充成分

希尔排序before: 三,一,5,7,二,肆,9,陆,10,八
早先化步长:拾
步长变为:4
对比 第4个元素:2,第0个元素:3
赋值 第五个要素二赋值为第0成分三
赋值 第0个因素二赋值为第四成分二
对比 第5个元素:4,第1个元素:1
对比 第6个元素:9,第2个元素:5
对比 第7个元素:6,第3个元素:7
赋值 第10个成分6赋值为第1成分7
赋值 第一个成分陆赋值为第九元素陆
对比 第8个元素:10,第4个元素:3
对比 第9个元素:8,第5个元素:4
上升的幅度变为:二
对比 第2个元素:5,第0个元素:2
对比 第3个元素:6,第1个元素:1
对比 第4个元素:3,第2个元素:5
赋值 第5个因素三赋值为第3成分伍
赋值 第②个成分3赋值为第陆因素三
对比 第5个元素:4,第3个元素:6
赋值 第四个成分肆赋值为第二成分陆
赋值 第三个要素四赋值为第伍成分4
对比 第6个元素:9,第4个元素:5
对比 第7个元素:7,第5个元素:6
对比 第8个元素:10,第6个元素:9
对比 第9个元素:8,第7个元素:7
增长幅度变为:1
对比 第1个元素:1,第0个元素:2
赋值 第3个成分一赋值为第0成分二
赋值 第0个成分一赋值为第二成分一
对比 第2个元素:3,第1个元素:2
对比 第3个元素:4,第2个元素:3
对比 第4个元素:5,第3个元素:4
对比 第5个元素:6,第4个元素:5
对比 第6个元素:9,第5个元素:6
对比 第7个元素:7,第6个元素:9
赋值 第多个要素柒赋值为第六成分九
赋值 第四个成分7赋值为第拾成分7
对比 第8个元素:10,第7个元素:9
对比 第9个元素:8,第8个元素:10
赋值 第7个成分8赋值为第柒因素十
赋值 第八个成分10赋值为第百分之九十分玖
赋值 第几个成分八赋值为第玖成分8
希尔排序after: 一,贰,3,肆,伍,陆,7,八,玖,十
堆排序before: 3,1,5,7,2,4,9,6,10,8
堆排序after: 1,2,3,4,5,6,7,8,9,10
[Finished in 0.1s]

 1 #由元素赋值的示例可以看到,不能为一个不存在的位置赋值。一旦初始化了一个列表,就不能再往这个列表中增加元素了。若需要往列表中增加元素,则需要将整个列表中的元素都复制一遍,再添加需要增加的元素。Python中是否提供了对应的方法帮助我们做这件事情呢?
 2 >>> tring=[1,2,3]
 3 >>> tring.append(4)
 4 >>> tring
 5 [1, 2, 3, 4]
 6 #由示例可以看到,可以使用append()方法解决前面的困惑。append()方法是用于在列表末尾添加新对象的方法。该方法的语法如下:
 7 list.append(obj)
 8 #此语法中list代表列表,obj代表需要添加到list列表末尾的对象。
 9 #由前面的输出结果得知:append()方法不是简单地返回一个修改过的新列表,而是直接修改原来的列表。例:
10 >>> tring=[1,2,3]
11 >>> tring.append('hello')       #添加字符串
12 >>> tring
13 [1, 2, 3, 'hello']
14 >>> s=['a','b','c']
15 >>> s
16 ['a', 'b', 'c']
17 >>> s.append(3)                   #添加数值
18 >>> s
19 ['a', 'b', 'c', 3]
20 #由上面的示例可以得知:可以往数字序列中添加字符串,也可以往字符串序列中添加数字。

非常的慢排序

3、删除成分

function quickSort(arr){
    //如果数组<=1,则直接返回
    if(arr.length<=1){
        return arr;
    }
    var pivotIndex=Math.floor(arr.length/2);
    //找基准,并把基准从原数组删除
    var pivot=arr.splice(pivotIndex,1)[0];
    //定义左右数组
    var left=[];
    var right=[];
    //比基准小的放在left,比基准大的放在right
    for(var i=0;i<arr.length;i++){
        if(arr[i]<=pivot){
            left.push(arr[i]);
        }
        else{
        right.push(arr[i]);
        }
    }
    //递归
    return quickSort(left).concat([pivot],quickSort(right));
}
var a1 = [3, 1, 5, 7, 2, 4, 9, 6, 10, 8];
console.log('排序before: ' + a1);
a1 = quickSort(a1);
console.log('排序after: ' + a1);
 1 #既然可以增加元素,是否可以删除元素呢?示例如下:
 2 >>> tring=['a','b','c','d','e']
 3 >>> len(tring)
 4 5
 5 >>> del tring[1]
 6 >>> print('删除第二个元素:',tring)
 7 删除第二个元素: ['a', 'c', 'd', 'e']
 8 >>> len(tring)
 9 4
10 #由上面的示例看到,可以使用del删除列表中的元素。上面的示例使用del删除了tring列表中的第二个元素,删除元素后,原来有5个元素的列表变成了只有4个元素的列表。使用del除了可以删除列表中的字符,也可以删除列表中的数字,示例如下:
11 >>> numbers=[1,2,3]
12 >>> len(numbers)
13 3
14 >>> del numbers[2]
15 >>> print('删除第3个元素:',numbers)
16 删除第3个元素: [1, 2]
17 >>> len(numbers)
18 2
19 #上面的输出结果已经从数字列表中删除了对应的数字。

排序before: 3,1,5,7,2,4,9,6,10,8
排序after: 1,2,3,4,5,6,7,8,9,10

end

归并排序

function merge(left,right) {
    var result = [];
    while(left.length>0&&right.length>0){
        if(left[0]<right[0]){
            result.push(left.shift());
        }else{
            result.push(right.shift());
        }
    }
    return result.concat(left).concat(right);
}
function mergeSort(arr){
    if(arr.length==1){
        return arr;
    }
    var mid = Math.floor(arr.length/2);
    var left = arr.slice(0,mid);
    var right = arr.slice(mid);
    return merge(mergeSort(left),mergeSort(right))
}
var a1 = [3, 1, 5, 7, 2, 4, 9, 6, 10, 8];
console.log('排序before: ' + a1);
a1 = mergeSort(a1);
console.log('排序after: ' + a1);

排序before: 3,1,5,7,2,4,9,6,10,8
排序after: 1,2,3,4,5,6,7,8,9,10
[Finished in 0.1s]