2016-03-18 3 views
0

У меня есть эта функция:Сортировка массива javascript, когда значение поля может быть нулевым?

tests.sort(function (a, b) { 
    var diff = a.title.localeCompare(b.title); 
    return diff == 0 ? b.modifiedDate.localeCompare(a.modifiedDate) : diff; 
}); 

Я использую его, чтобы отсортировать tests массив сначала title, а затем modifiedDate. Код работал, но теперь я обнаружил, что он дает ошибку. Когда значение modifiedDate равно null, и когда это происходит, сбой сравнивается.

Как я могу сделать так, чтобы, если modifiedDate имеет значение null, сортировка по-прежнему работает и помещает эти строки после строк с измененной датой, которая не является нулевой?

+0

я иногда мусор аргументы, как я работаю вниз возможности, так что вы можете сделать что-то вроде 'б = b.modifiedDate || 0, а = a.modifiedDate || 0 ; 'перед сравнением. – dandavis

+0

Возможно, вы захотите взглянуть на [это] (http://stackoverflow.com/a/19103480/1048572) – Bergi

+0

Простой 'diff == 0 && b.modifiedDate ...?' Не работает? – vol7ron

ответ

1

Думая от верхней части головы, сортировать по названию, а затем ModifiedDate с нулями последние:

tests.sort(function (a, b) { 
    var diff = a.title.localeCompare(b.title), 
     has_modifiedDate = a.modifiedDate && b.modifiedDate && true || false; 


    if (diff === 0) { 
    if (has_modifiedDate) { 
     return a.modifiedDate.localeCompare(b.modifiedDate) 
    } 
    else { 
     if (! b.modifiedDate){ 
     if (! a.modifiedDate) 
      return 0; 
     else 
      return -1; 
     } 
     else { 
     if (! a.modifiedDate) 
      return 1; 
     else 
      return -1; 
     } 
    } 
    } 
    else 
    return diff; 
}); 

Примечания: это непроверенное и здесь очень поздно/рано. Если это неверно, отправьте сообщение и я удалю или обновлю; но способ устать думать.

Быстрый набор данных, с которым вы можете попробовать: заполнить с тем, что данные, которые вы хотите:

var tests = [ 
    {modifiedDate:'z', title:'foo'}, 
    {modifiedDate:'a', title:'foo'}, 
    {modifiedDate:null, title:'foo'}, 
    {modifiedDate:'a', title:'foo'}, 
    {modifiedDate:'null', title:'foo'}, 
    {modifiedDate:'z', title:'foo'}, 
    {modifiedDate:'z', title:'bar'}, 
    {modifiedDate:'a', title:'bar'}, 
    {modifiedDate:null, title:'bar'} 
]; 
+0

Вы могли бы сократить его (например, опустив второй 'if (!.m.midifiedDate)'), но он кажется правильным – Bergi

+0

Я не тестировал, но я думаю, что нужно нажать на нули в нижней части stack, потому что он говорит, что если оба они имеют одинаковый заголовок, а следующий элемент имеет модифицированную дату, но текущий элемент этого не делает. Похоже, что 'if' может быть автономным, а оболочка' else' не нужна – vol7ron

+0

Просто любопытно: почему лишнее истинное раньше или? a.modifiedDate && b.modifiedDate && true || ложный. Раньше я этого не видел. – Will

0

Попробуйте это:

tests.sort(function(a, b) { 
    var diff = a.title.localeCompare(b.title); 
    return diff == 0 ? (a.modifiedDate ? a.modifiedDate.getTime() : Infinity) - (b.modifiedDate ? b.modifiedDate.getTime() : Infinity) : diff; 
}) 
+1

Возможно, вы даже просто выполните 'return diff || (... - ...); ' – Bergi

+0

Я бы поддержал это (приятное решение!), Но я думаю, что' .modifiedDate' - это строка (имеющая метод '.localeCompare'), а не объект' Date', несмотря на название , – Bergi

+0

@Bergi - Мне нравится diff || (...) идея - спасибо. Это чище. – Will

Смежные вопросы