Javascript-форум (https://javascript.ru/forum/)
-   Events/DOM/Window (https://javascript.ru/forum/events/)
-   -   Удаление одинаковых элементов массива (https://javascript.ru/forum/events/45211-udalenie-odinakovykh-ehlementov-massiva.html)

Ваяс 19.02.2014 07:42

Удаление одинаковых элементов массива
 
Помогите удалить одинаковые элементы массива, оставляя те что не повторялись
var array = [1, 2, 1, 10, 5, 3, 4, 40, 50], i = array.length, result = [];

array.sort(function(a,b) {
    return b-a;
});

while(i--){
    if(result.join().search(array[i]+'\\b') == '-1') {
        result.push(array[i]);
    }
}

alert(result);

Т.е. если значение повторялось, его не пишем вообще
[2, 10, 5, 3, 4, 40, 50]

рони 19.02.2014 12:45

Ваяс,
:-?
var array = [1, 2, 1, 10, 5, 3, 4, 40, 50],
     i = array.length,
     result = [];
 array.sort(function (a, b) {
     return a - b;
 });
 for (var i = 0; i < array.length; i++) {
     array[i] != array[i - 1] && array[i + 1] != array[i] && result.push(array[i])
 }
 alert(result);

Deff 19.02.2014 15:55

var arr = [1, 2, 1, 10, 5, 3, 4, 40, 50],
bound = '\n\n===@@@==\n\n',
tststr = bound + arr.join(bound+bound) + bound,
out=[];
 for (var i = 0; i < arr.length; i++) {
     if(tststr.split(bound +arr[i] + bound).length <3)out.push(arr[i])
 }
alert(out)

danik.js 19.02.2014 16:06

Цитата:

Сообщение от Deff
bound = '\n\n==123==\n\n'

Вместо этих ужасных костылей лучше es5-shim.js подключить (или выковырять только функцию Array.prototype.indexOf)

Deff 19.02.2014 16:23

danik.js,
:) У меня до сих пор на сервисе требование Ие7
1. Костыль не длиннее
2. Если разобрать исходники, всё в конце концов делается через строчные операторы, т.е по идее скорость обработки должна возрастать
3. Для данного случая можно bound = ','

danik.js 19.02.2014 16:57

Цитата:

Сообщение от Deff
У меня до сих пор на сервисе требование Ие7

es5-shim.js работает даже в IE5.5 если ты не в курсе. Так что не знаю к чему твой довод
1) Не длинее, но ужаснее, плюс имеет ограниченную применимость, в отличие от [].indexOf
2) Ха-ха, будешь мне тут за скорость говорить, когда у тебя на каждой итерации идет создание массива через split()
3) Вот именно. К чему было бороду лепить.

Deff 19.02.2014 18:29

Цитата:

Сообщение от danik.js
1) Не длинее, но ужаснее,

:) Имхо: А что твоё мнение определяющее во всём инете ?
Мне например Ван Гог не импонирует...
Цитата:

плюс имеет ограниченную применимость, в отличие от [].indexOf
Приведи пример, второе: Вы слишком серьёзно подходите к кодам выложенным в качестве развлечения!
Цитата:

Сообщение от danik.js
2) Ха-ха, будешь мне тут за скорость говорить, когда у тебя на каждой итерации идет создание массива через split()

Выложи свой код, создадим тест сравнения, для текстовых переменных как то тестировал, (ксать не оптимизировал пока по скорости

danik.js 19.02.2014 20:05

Цитата:

Сообщение от Deff
Выложи свой код

var array = [1, 2, 1, 10, 5, 3, 4, 40, 50];
var result = [];
for (var i = 0; i < array.length; i++) {
    var item = array[i];
    if (array.indexOf(item, i + 1) === -1 && (i === 0 || array.lastIndexOf(item, i - 1) === -1))
        result.push(item);
}
alert(result);

danik.js 19.02.2014 20:10

Цитата:

Сообщение от Deff
создадим тест сравнения

Ну что ж, давай!

/**
 * @author danik.js
 **/
function test1() {
    var array = [1, 2, 1, 10, 5, 3, 4, 40, 50];
    var result = [];
    for (var i = 0; i < array.length; i++) {
        var item = array[i];
        if (array.indexOf(item, i + 1) === -1 && (i === 0 || array.lastIndexOf(item, i - 1) === -1))
            result.push(item);
    }
    return result;
}

/**
 * @author Deff
 **/
function test2() {
    var array = [1, 2, 1, 10, 5, 3, 4, 40, 50];
    var bound = ',';
    var tststr = bound + array.join(bound+bound) + bound;
    var result = [];
     for (var i = 0; i < array.length; i++) {
        var item = array[i];
        var t = bound +item + bound;
        if (tststr.indexOf(t) === tststr.lastIndexOf(t))
            result.push(item);
     }
    return result;
}

/**
 * @author рони
 **/
function test3() {
    var array = [1, 2, 1, 10, 5, 3, 4, 40, 50];
    var result = [];
    array.sort(function (a, b) {
        return a - b;
    });
    for (var i = 0; i < array.length; i++) {
        var item = array[i];
        if (item != array[i - 1] && array[i + 1] != item)
            result.push(item);
    }
    return result;
}



/**
 * @author Дзен-трансгуманист (danik.js edition)
 **/
function test4(){
    var array = [1, 2, 1, 10, 5, 3, 4, 40, 50];
    var uniqueness = [];
    var result = [];
    for (var i = 0; i < array.length; i++) {
        var item = array[i];
        switch (uniqueness[item]) {
          case undefined:
              uniqueness[item] =  true;
              break;
          case true:
              uniqueness[item] = false;
        }
    }

    for (var i = 0; i < array.length; i++) {
        var item = array[i];
        if (uniqueness[item])
            result.push(item);
    }
    return result;
}

/**
 * @author BallsShaped
 **/
function test6(){
    var array = [1, 2, 1, 10, 5, 3, 4, 40, 50];
    var result = [];
    for (var i = 0; i < array.length; i++) {
        var item = array[i];
        if (array.indexOf(item) == array.lastIndexOf(item))
            result.push(item);
    }
    return result;
}

/**
 * @author Дзен-трансгуманист
 **/
function test5(){
  var array = [1, 2, 1, 10, 5, 3, 4, 40, 50];
  var uniqueness = new Map();
  var result = [];

  for ( var i = 0; i < array.length; i++ ) {
    var value = array[ i ];
    switch ( uniqueness.get( value )) {
      case undefined: uniqueness.set( value, true ); return;
      case true: uniqueness.set( value, false );
    }
  }

  for ( var i = 0; i < array.length; i++ ) {
      var item = array[ i ];
      if ( uniqueness.get( value ) )
        result.push( item );
  }
  return result;
}

console.time('danik.js');
for (var i = 0; i < 1000000; i++)
    test1();
console.timeEnd('danik.js')



console.time('Deff');
for (var i = 0; i < 1000000; i++)
    test2();
console.timeEnd('Deff')



console.time('рони');
for (var i = 0; i < 1000000; i++)
    test3();
console.timeEnd('рони')

console.time('Дзен-трансгуманист (danik.js edition)');
for (var i = 0; i < 1000000; i++)
    test4();
console.timeEnd('Дзен-трансгуманист (danik.js edition)')

console.time('BallsShaped');
for (var i = 0; i < 1000000; i++)
    test6();
console.timeEnd('BallsShaped')

console.time('Дзен-трансгуманист');
for (var i = 0; i < 1000000; i++)
    test5();
console.timeEnd('Дзен-трансгуманист')


Мои результаты в хроме:
Код:

danik.js: 725.000ms
Deff: 5175.000ms
рони: 1448.000ms

Хорошо бы конечно генерить рандомные массивы разного размера, но как-то лень мне...
Думаю на больших массивах вариант рони окажется быстрей.

BallsShaped 19.02.2014 20:19

То ли я задачу не понял, то ли это конкурс самого нечитаемого кода. Не проще ли так:
.filter(function (item, index, array) {
    return array.indexOf(item) == index;
})


Часовой пояс GMT +3, время: 18:58.