关于实现js冒泡排序可视化的思路分析

需求分析



  • 两个区域:

    • 操作区域:可供操作的区域

    • 呈现区域:将数据可视化的区域



  • 两个模块(操作区域内):

    • 输入模块:可供数据输入的模块

    • 功能模块:可选功能的模块



  • 五个功能(功能模块内):

    • 数据插入功能

    • 数据删除功能

    • 随机生成数据功能(1~100)

    • 数据排序功能(冒泡排序)

    • 数据打乱排序功能



功能实现设想


流程图


流程图

具体实现分析


基本思路:将数据储存在数组dataList[ ]中,根据需求对数组进行操作,并将操作后的数组渲染在网页上(即数据可视化)


实现过程


  1. 添加函数

    • 渲染函数


      渲染函数主要是通过dom操作,将数据添加到文档中。关于数据可视化,我采用的方式是以div作为一个数据bar,根据数据的大小不同,动态地给每个div设定高度,并且给每个div添加背景颜色,这样,在网页上看起来,就和柱状图一样了。

      function render(){

      var numList = document.getElementById("num-list");

      //每次调用渲染函数都将原numList里内容清空并重新渲染

      numList.innerHTML = "" ;

      for(var m = 0; m < dataList.length; m++){

      numList.innerHTML += "

      " + "
      " ;

      //取得包含数据的div的nodelist

      var dataDiv = numList.querySelectorAll("div");

      //给每个数据的div设定高度

      dataDiv[m].style.height = dataList[m]*5 + "px";

      }

      }





    • 打乱排序函数


      因为js的数组十分强大,自带sort()方法,所以我们只需要随机生成-1(正序)或者1(倒序),sort方法会自动帮我们对数组进行处理。
      function randomSort(){

      return Math.random()>0.5?-1:1;

      }



    • 随机生成函数


      与打乱排序函数相同,这个函数里同样使用了Math.random()方法,这个方法随机生成[0,1)范围内的数字,只要稍作变化,便能得到想要的[1,100]内的随机数。

      function randomGeneration(){

      for(var x=0; x<19; x++){
      dataList[x] = parseInt(Math.random()*100+1);
      }
      }



    • 冒泡排序函数

      function sortNum(arr){

      for (var i = arr.length-1; i > 0; i--) {

      for(var j = 0; j < i; j++){

      if (arr[j] > arr[j+1]) {

      var temp = arr[j];

      arr[j] = arr[j+1];

      arr[j+1] = temp;

      //将每一次交换的数组存到state中,state是数组的数组

      state.push(JSON.parse(JSON.stringify(arr)));

      }

      }

      }

      }


      关于这个排序函数,其实没有太多需要描述的地方,就是一个很简单的冒泡排序。值得一提的是,后面的state是一个数组,通过JSON数据格式,将每一次移动后原来数据的状态储存到了state中,在后面我们会根据这个state进行操作,以实现数据bar随着排序过程移动的视觉效果。





  2. 给各个按钮绑定事件


    设定一个初始函数init(),在init()中给各个按钮绑定事件,然后在最后调用init()函数即可。



    btn.onclick = function(){

    //添加事件

    }




    具体来说,一共有七个按钮,来实现五个功能,他们分别是:向左插入数据、向右插入数据、从左边删除数据、从右边删除数据、冒泡排序、打乱排序、随机生成数据。

    • 向左插入数据


      先使用dom操作获得用户输入的数据,然后通过数组的unshift()方法,将数据从数组坐标较小的那一方(即前方/左方)插入数组,然后将数组渲染在页面上。

      inleftBtn.onclick = function(){

      var data = document.getElementById("num- input").value.trim();

      dataList.unshift(data);

      render();
      }


      向右插入数据的操作同理,区别在于使用的是数组的push()方法。



    • 从左边删除数据


      删除数据的操作与插入数据的操作也很相似,原理也是对数组进行处理之后,进行渲染。

      outLeftBtn.onclick = function(){

      var data = document.getElementById("num-input").value.trim();

      dataList.shift(data);

      render();

      }


      shift()方法帮助我们从数组前方(视觉效果为左)删除数组元素。从右边删除数组使用pop()方法。



    • 冒泡排序
      sort.onclick = function(){

      sortNum(dataList);

      var int = setInterval(forSortRender, 100);

      //专门给冒泡排序写一个渲染函数

      function forSortRender(){

      var s ;

      s = state.shift();

      var numList = document.getElementById("num-list");

      numList.innerHTML = "" ;

      if (s !== undefined) {

      for(var m = 0; m < s.length; m++){

      numList.innerHTML += "

      " + "
      " ;

      //取得包含数据的div的nodelist

      var dataDiv =
      numList.querySelectorAll("div");

      //给每个数据的div设定样式

      dataDiv[m].style.height = s[m]*5 + "px";

      }

      }

      //避免state为空之后,页面也变空

      else{

      render();

      window.clearInterval(int);

      }

      }

      }


      之前我们提到,在写冒泡排序函数的时候,创建了一个state数组,用来存储每一趟排序后的数组状态,现在就到了它派上用场的时候。在我们专门为排序过程写的渲染函数中,shift()方法弹出state中第一个数组,即进行了第一次交换后的数组,并返回它,用变量s来保存。此时将s中的数据依次渲染在页面上。setInterval()方法会每隔100ms调用一次这个渲染函数。于是在100ms之后,state又弹出最前面的一个数组,这个数组是原来的dataList[ ]进行了两次交换之后的数组,将它渲染出来,我们在视觉上就形成了数据bar在移动的错觉。


      这样,在弹出了交换次数个数组之后,state[ ]变为空,s取不到任何值,就有可能出现排序完成后页面突然变空得情况。于是设置if条件,当s的值为undefined时,使用原来的渲染函数render()渲染排好序的原数组dataList[ ],并且使用clearInterval()停止调用专门给排序写的forSortRender()函数。







待改进的地方



  1. 点击事件实现得很不优雅,每一个按钮都要写一串onclick(),如果使用addEventLister()方法大概会好很多



  2. 用一个div盒子实现数据bar似乎有些简单粗暴?暂时没想到更好的方法



  3. 渲染函数写了两次,这个有点明显的要功能不要性能的意思,应该可以改进。



  4. 在用户输入数据时未作处理,可能收到非法字符。这个是待添加的功能,因为正则表达式没有系统地学习,想找机会认真地学习一遍再来改。



  5. 待添加其他几种排序方式,如快排、简单选择排序等,顺便巩固数据结构的知识



  6. 待改进样式,待添加颜色选择功能。前端工作者不论何时对于自己手里出来的界面都不能马虎才是!



总结




这次demo练习学到了不少js和dom方面的知识,小白表示很满足,但是实现得比较糙,需要改进的地方也很多,学习之路任重道远,加油↖(ω)↗




demo地址




https://github.com/escawn/dailyDemo/tree/master/jsVisualSort


你可能感兴趣的:(关于实现js冒泡排序可视化的思路分析)