【问题标题】:why does this list-sorter crash?为什么这个列表排序器会崩溃?
【发布时间】:2014-01-18 23:23:39
【问题描述】:

此页面在运行时崩溃:

<head>
<script>
    var list = [2, 4, 6, 8, 10, 12, 14, 16, 18, 20, 19, 17, 15, 13, 11, 9, 7, 5, 3, 1];
    var listOrdered = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20];
    var loopCount = 0;

    while (list !== listOrdered) {
        if (list[loopCount] > list[loopCount + 1]) {
            var lower = list[loopCount + 1];
            var higher = list[loopCount];
            list[loopCount] = lower;
            list[loopCount + 1] = higher;
        }
        if (loopCount === 19) {
            loopCount = 0;
        } else {
            loopCount = loopCount + 1;
        }
    }
</script>
</head>

</html>

我能做些什么来稳定它?

据我所知,逻辑与我预期的一样正确。 这纯粹是娱乐性的实验。

经过进一步发展,比较的问题不再存在:

<!doctype html>
<html>
<head>
    <script>
    var sweeps = 0;
    var swaps = 0;
    var list = [25, 21, 4, 23, 32, 2, 40, 8, 27, 9, 29, 33, 31, 14, 12, 16, 35, 18, 37, 20, 39, 19, 38, 17, 36, 15, 34, 13, 6, 11, 30, 10, 28, 7, 26, 5, 1, 3, 22, 24];
    var loop = 0;
    var swapped = 0;
    var ordered = 0;

    while (ordered !== 1) {
        if (list[loop] > list[loop + 1]) {
            var lower = list[loop + 1];
            var higher = list[loop];
            list[loop] = lower;
            list[loop + 1] = higher;
            swapped = 1;
            swaps = swaps + 1;
        }
        if (loop === list.length - 1) {
            if (swapped === 0) {
                ordered = 1;
            }
            swapped = 0;
            loop = 0;
        } else {
            loop = loop + 1;
        }
        sweeps = sweeps + 1;
    }
    alert("list: " + list);
    alert("Sweeps: " + sweeps + ", Swaps: " + swaps);
</script>

(就像“cooky monster”所暗示的那样)

【问题讨论】:

    标签: javascript algorithm sorting crash logic


    【解决方案1】:

    因为数组对象永远不会是同一个对象,即使它们的内容最终相同(JavaScript 在对象(包括数组)上使用比较运算符时不会比较值,而是它们是否是相同的对象)。您可以将它们都序列化为字符串并比较字符串,但是,为了适合您的方法的快速和肮脏的比较:

    <head>
    <script>
    var list = [2, 4, 6, 8, 10, 12, 14, 16, 18, 20, 19, 17, 15, 13, 11, 9, 7, 5, 3, 1];
    var listOrdered = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20];
    var loopCount = 0;
    
    while (JSON.stringify(list) !== JSON.stringify(listOrdered)) {
        if (list[loopCount] > list[loopCount + 1]) {
            var lower = list[loopCount + 1];
            var higher = list[loopCount];
            list[loopCount] = lower;
            list[loopCount + 1] = higher;
        }
        if (loopCount === 19) {
            loopCount = 0;
        } else {
            loopCount = loopCount + 1;
        }
    }
    alert(JSON.stringify(list)) // [1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20]
    </script></head></html>
    

    JSON.stringify在旧版浏览器中默认不可用,所以如果需要支持旧版浏览器,可以使用https://github.com/douglascrockford/JSON-js/blob/master/json2.js

    【讨论】:

      【解决方案2】:

      我只使用一个标志来指示您是否必须在迭代期间交换值,而不是进行比较。如果是这样,请将计数器重置为 0 并重置标志。如果没有,你就完成了。

      var list = [2, 4, 6, 8, 10, 12, 14, 16, 18, 20, 19, 17, 15, 13, 11, 9, 7, 5, 3, 1];
      var loopCount = 0;
      var swapped;
      
      while (true) {
          if (list[loopCount] > list[loopCount + 1]) {
              var lower = list[loopCount + 1];
              var higher = list[loopCount];
              list[loopCount] = lower;
              list[loopCount + 1] = higher;
              swapped = true;     // Set the flag indicating we swapped a pair of values.
          }
          if (loopCount === 19) { // At the end of a full iteration...
              if (swapped) {      //  check to see if we had occasion to swap..
                  swapped = false;//  and if so, reset the flag, and start again..
                  loopCount = 0;
              } else
                  break; // or if not, we're done sorting.
          } else {
              loopCount = loopCount + 1;
          }
      }
      

      这将比任何类型的数组比较快得多。

      【讨论】:

      • 已建议我避免语义的 while (true) 循环。这有多重要?
      • @Wetware.:这纯粹是一个偏好问题。其他人会建议始终将所有逻辑放在块中。最终,因为您在循环中将loopCount 重置为0,所以如果逻辑不正确,您总是会面临无限循环的风险。您的 ordered != 1 也可以正常工作,尽管我倾向于使用布尔值,但这也只是一个偏好问题。 :-)
      猜你喜欢
      • 2017-04-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-02-04
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多