2015-09-26 86 views
0

我試圖練習我的Javascript印章。對於一些原因,每當我把這個Javascript代碼是否會導致無限循環?

function swap (pair) 
{ 
    temp = pair.first; 
    pair.first = pair.second; 
    pair.second = temp; 
} 

function stable_partition (arr, unpred) 
{ 
    // each x in arr for which upred(x)=true is 
    // moved to the right and each for which 
    // unpred(x)=false is moved to the left of 
    // the array arr 

    var i = 0, j = (arr.length - 1); 
    while (i < j) 
    { 
     while (!unpred(arr[i]) && (i < j)) ++i; 
     while ( unpred(arr[j]) && (i < j)) --j; 
     swap({ first : arr[i], second: arr[j] }); 
    } 
} 

var MyUnaryPredicate = function (x) { return x == 0; } 
var MyArray = [0, 0, 4, 0, 69, 1932]; 
stable_partition(MyArray,MyUnaryPredicate); // should move all the zeros to the back of MyArray 

for (var k = 0, n = MyArray.length; k < n; ++k) $('#resultdiv').append(MyArray[k] + ' '); 

JSFiddle通過谷歌瀏覽器使用的CPU射擊,我的電腦聽起來像它會爆炸,該代碼永遠不會完成運行。我的代碼有什麼問題,或者是我的電腦鋪蓋?

另外,我想知道如果我可以,因爲每次進入循環體的時候,i < j檢查2次unnessary(因爲在過程

while (i < j) 
{ 
    while (!unpred(arr[i]) && (i < j)) ++i; 
    while ( unpred(arr[j]) && (i < j)) --j; 
    swap({ first : arr[i], second: arr[j] }); 
} 

削減輕微冗餘操作它已經在while條件下檢查過)。

+1

你的'swap'函數做了兩件事:1)它改變了全局'temp'變量。 2)它修改傳入的對象。你對'swap'的調用傳遞一個臨時對象:'swap({...});'該對象在函數返回後被銷燬,所以它沒關係被修改了(並且你沒有使用'window.temp')。你的'swap'調用不起作用。 – melpomene

+0

我以爲對象是作爲引用傳遞的。這就是爲什麼我使用一個對象來讓'arr [i]'和'arr [j]'進入函數。 –

+0

是的,這就是爲什麼該函數能夠修改調用者的對象。但是對象中的值只是'arr [i]'和'arr [j]'的副本,它們保持不變。 – melpomene

回答

0

你可以做一個交換功能這樣

function swap(arr, first, second) { 
    var temp = arr[first]; 
    arr[first] = arr[second]; 
    arr[second] = temp; 
} 

也有可能使while循環略短,但它不會跑得更快。

while (i < j) 
{ 
    if(!unpred(arr[i])) ++i; 
    else if(unpred(arr[j])) --j; 
    else swap(arr, i, j); 
} 
0

如果你想要的是讓所有滿足謂詞的左側和元素的所有其他人的權利(或反之亦然,你只需要調整的返回值),我認爲你是多少最好用類似這樣的東西:

function stable_partition (arr, unpred) 
{ 
    var retArray1 = []; 
    var retArray2 = []; 
    var retArrayIndex1 = 0; 
    var retArrayIndex2 = 0; 

    for (var i=0; i < arr.length; i++) 
    { 
     if (!unpred(arr[i])) 
     { 
      retArray1[retArrayIndex1] = arr[i]; 
      retArrayIndex1++; 
     } else { 
      retArray2[retArrayIndex2] = arr[i]; 
      retArrayIndex2++; 
     } 
    } 

    return retArray1.concat(retArray2); 
}