Sorting possibly unstable and general jsfiddle/jquery problem

Posted on

Problem

I have a simple sorting algorithm that I was told is possibly unstable. I’m wondering what in the sort is unstable. I have test cases written to test all fields with no issues.

A secondary problem is that jQuery is not appending the rows for some reason (works fine in local and server environments).

http://jsfiddle.net/SucGH/

var applyData = function (dataSet) {
    $('#healthplans tbody').empty();
    for (var i = 0; i < dataSet.length; i++) {
        var itemRow = '';
        for (item in dataSet[i]) {
            var newItem = dataSet[i][item];
            if (typeof newItem === 'number') newItem = "$" + newItem;
            itemRow += '<td>' + newItem + '</td>';
        }
        $('#healthplans tbody').append('<tr>' + itemRow + '</tr>');
    }
}

var order = '';
var sortDataByField = function (field, newOrder, test) {
    if (!newOrder) order = (order == 'asc') ? 'desc' : 'asc';
    else order = newOrder;
    if (field) {
        jsonData.sort(function (a, b) {
            if (typeof b[field] === 'string') {
                var bfield = b[field].toUpperCase();
                var afield = a[field].toUpperCase();
                if (bfield < afield) return (order == 'asc') ? -1 : 1;
                if (bfield > afield) return (order == 'asc') ? 1 : -1;
                return 0;
            } else if (typeof b[field] === 'number') {
                if (order == 'desc') return b[field] - a[field]
                else if (order == 'asc') return a[field] - b[field]
                return 0;
            }
        });
        if (!test) {
            applyData(jsonData);
        }

    } else {
        return 'Field and/or order not properly defined';
    }
}

Solution

You are using the built-in sort of Array, which is not guaranteed to be stable per the documentation. You will have to write your own sort algorithm from scratch.

Other than that,

  • It is considered better form to have a single comma separated var statement
  • Calling append() inside a loop gives poor performance, just collect everything in a string, and call append() once
  • You could cache $('#healthplans tbody') since you call it more than once
  • You should not skip the newline after an if statement
  • You should consider using hasOwnProperty when using for (item in dataSet[i])
  • You did not declare item with var
  • You call too many things item, I am assuming that the property in dataSet is more of itemId ?
  • All that gives this :

    var applyData = function (dataSet) {
        var i,
            itemId
            item,
            itemRow, 
            html = '';            
            $table = $('#healthplans tbody'),
    
        $table.empty();
        for (i = 0; i < dataSet.length; i++) {
            itemRow = '';
            for (itemId in dataSet[i]) {
                item= dataSet[i][itemId];
                if (typeof item=== 'number') 
                  item= '$' + item;
                itemRow += '<td>' + item+ '</td>';
            }
            html += '<tr>' + itemRow + '</tr>';
        }
        $table.append( html );        
    }
    

I did not comment on the sort function, since that most likely will be throw away.

Leave a Reply

Your email address will not be published. Required fields are marked *