簡體   English   中英

底部帶有空格的日期的Javascript自定義排序功能

[英]Javascript custom sort function for dates with blanks at the bottom

我正在使用表格插件(ng-grid)顯示一堆數據,其中包括一些日期列。 該插件允許使用“ sortingAlgorithm”函數進行自定義排序,該函數接受“ aDate”和“ bDate”參數。 日期以字符串形式存儲在數據庫中,我正在使用Moment將其轉換為日期對象。 這是排序功能:

sortingAlgorithm: function (aDate, bDate) {
    var a = moment(aDate, 'MM/DD/YYYY');
    var b = moment(bDate, 'MM/DD/YYYY');
    if (a.isBefore(b)) {
        return -1;
    }
    else if (a.isAfter(b)) {
        return 1;
    }
    else {
        return 0;
    }
}

這可以正常工作,但是如果沒有日期,只是一個空字符串,則空格按升序排列在列表的末尾,而按降序排列在開始的末尾。 如何確保空白(“”)始終移到列表的底部?

謝謝。

更新

我認為這與UI-Grid庫特別相關。 參見rowSorter.js 它似乎在內部處理null,這使我的mojo感到困惑。 我也看不到選擇的排序方向暴露在什么地方供我使用...

我正在添加“ angular-ui-grid”標簽...

因此,我復制了ui-grid內部特定於日期的排序函數,並用我自己的函數替換了其“ handleNulls”函數調用(請參見下文):

sortingAlgorithm: function (a, b) {
    var nulls = handleNulls(a, b);
    if ( nulls !== null ){
        return nulls;
    } else {
        if (!(a instanceof Date)) {
            a = new Date(a);
        }
        if (!(b instanceof Date)){
            b = new Date(b);
        }
        var timeA = a.getTime(),
            timeB = b.getTime();

        return timeA === timeB ? 0 : (timeA < timeB ? -1 : 1);
    }
}

這是ui-grid的“ handleNulls”函數的副本,已更新為始終根據方向將空值強制到底部:

function handleNulls(a, b) {
    if ((!a && a !== 0 && a !== false) || (!b && b !== 0 && b !== false)) {
        if ((!a && a !== 0 && a !== false) && (!b && b !== 0 && b !== false)) {
            return 0;
        }
        else if (!a && a !== 0 && a !== false && vm.direction === 'asc') {
            return 1;
        }
        else if (!b && b !== 0 && b !== false && vm.direction === 'asc') {
            return -1;
        }
        else if (!a && a !== 0 && a !== false && vm.direction === 'desc') {
            return -1;
        }
        else if (!b && b !== 0 && b !== false && vm.direction === 'desc') {
            return 1;
        }
    }
    return null;
};

vm.direction來自ui-grid的onRegisterApi回調,該回調具有用於進行排序更改的鈎子:

onRegisterApi: function (gridApi) {
    vm.gridApi = gridApi;
    vm.gridApi.core.on.sortChanged($scope, function(grid, sortColumns) {
        if (sortColumns[0]) {
            vm.direction = sortColumns[0].sort.direction;
        } else {
            vm.direction = 'none';
        }
    });
}

奇跡般有效!

如果ng-grid插件使用排序算法,然后應用reverse()以降序排序,那么我認為您不能在項目末尾強制使用。 我猜您將不得不覆蓋插件中的排序。

為了測試空字符串,您可以將比較條件放在第一位,因此''總是結尾”。 這樣,您不會通過強制moment.js解析空字符串來創建無效日期。

sortingAlgorithm: function(aDate, bDate) {
  if (aDate === '') {
    return 1;
  }
  if (bDate === '') {
    return -1;
  }

  var a = moment(aDate, 'MM/DD/YYYY');
  var b = moment(bDate, 'MM/DD/YYYY');

  if (a.isBefore(b)) {
    return -1;
  } else if (a.isAfter(b)) {
    return 1;
  } else {
    return 0;
  }
}

嘗試這個:

var direction=1;
var sortingAlgorithm= function (aDate, bDate) {
    var a=moment(aDate,'MM/DD/YYYY');
    var b=moment(bDate,'MM/DD/YYYY');
    if (!a.isValid()) return 1;
    if (!b.isValid()) return -1;
    return direction*((+a)-(+b));
}

它考慮了日期和方向(1或-1)的有效性,因此無效日期始終在底部。

這是我基於此和另一個使用moment.js的線程得出的結果

 var sortmedate = function (a, b, rowA, rowB, direction) {
            //the dates do not get sorted properly so we need moment.js and this method.
            var dateFormat = 'MM/DD/YYYY'; //todo: pass in date format from mvc controller.

            if (!a && !b) {
                return 0;
            }

            if (!a) {
                return 1;
            }

            if (!b) {
                return -1;
            }

            var firstDate = moment(a, dateFormat);
            if (!firstDate.isValid()) {
                return -1;
            }

            var secondDate = moment(b, dateFormat);
            if (!secondDate.isValid()) {
                return 1;
            }

            if (firstDate.isSame(secondDate)) {
                return 0;
            } else {
                return firstDate.isBefore(secondDate) ? -1 : 1;
            }

        };

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM