web-dev-qa-db-ja.com

javascript配列から要素を削除するきれいな方法(jQuery、coffeescriptを使用)

これに関して多くの質問があります。特に、 jQueryバージョンの配列に含まれるスプライスメソッドを使用したソリューション など。しかし、それらはすべて複雑で迷惑なようです。

Javascript、jQuery、coffeescriptのパワーを組み合わせて、javascript配列から要素を削除する最もクリーンな方法は何ですか?インデックスが事前にわかりません。コード内:

a = [4,8,2,3]
a.remove(8)     # a is now [4,2,3]

適切な組み込みメソッドに失敗した場合、javascript配列を拡張してそのようなメソッドをサポートするクリーンな方法は何ですか?それが役立つ場合、私は本当に配列として配列を使用しています。ソリューションは、jQueryサポートを備えたcoffeescriptでうまく機能することが理想的です。また、速度を気にすることはできませんでしたが、代わりに明確でシンプルなコードを優先しました。

59
Peter

CoffeeScript:

Array::remove = (e) -> @[t..t] = [] if (t = @indexOf(e)) > -1

これは、tが見つかったインデックスの位置e(実際に見つかった場合はt > -1)。 Coffeescriptはこれを次のように変換します。

Array.prototype.remove = function(e) {
    var t, _ref;
    if ((t = this.indexOf(e)) > -1) {
        return ([].splice.apply(this, [t, t - t + 1].concat(_ref = [])), _ref);
    }
};

そして、CoffeeScriptとjQueryを使用して、一致するすべての要素を削除し、新しい配列を返す場合:

Array::remove = (v) -> $.grep @,(e)->e!=v

次のように変換されます:

Array.prototype.remove = function(v) {
    return $.grep(this, function(e) {
        return e !== v;
    });
};

または、jQueryのgrepなしで同じことを行います。

Array::filterOutValue = (v) -> x for x in @ when x!=v

次のように変換されます:

Array.prototype.filterOutValue = function(v) {
    var x, _i, _len, _results;
    _results = [];
    for (_i = 0, _len = this.length; _i < _len; _i++) {
        x = this[_i];
        if (x !== v) {
            _results.Push(x);
        }
    }
    return _results;
};
87
Amir

バニラジャバスクリプトの使用:

Array.prototype.remove = function(elem) {
    var match = -1;

    while( (match = this.indexOf(elem)) > -1 ) {
        this.splice(match, 1);
    }
};

var a = [4, 8, 2, 3];

a.remove(8);

JQueryのみ:

jQuery.removeFromArray = function(value, arr) {
    return jQuery.grep(arr, function(elem, index) {
        return elem !== value;
    });
};

var a = [4, 8, 2, 3];

a = jQuery.removeFromArray(8, a);
27
jAndy

これはjQueryを使用すると非常に簡単です。

_var index = $.inArray("value", myArray);
if(index != -1)
{
  myArray.splice(index, 1);
}
_

ノート:

spliceは削除された要素を返すため、myArray = myArray.splice()を実行しないでください。 myArray.splice(index,1)は、「配列からインデックス_'index'_の配列要素を削除する」ことを意味します。

_$.inArray_は、探している値の配列内のインデックスを返します。値が配列内にない場合は-1を返します。

14
adavea

これはかなりきれいで理解しやすいようです。他の回答とは異なり、要素が複数回現れる可能性を考慮します。

Array.prototype.remove = function (value) {
    for (var i = 0; i < this.length; ) {
        if (this[i] === value) {
            this.splice(i, 1);
        } else {
           ++i;
        }
    }
}

CoffeeScriptの場合:

Array::remove = (value) ->
    i = 0
    while i < @length
        if @[i] == value
            @splice i, 1
        else
            ++i
    return @
9
Domenic

coffeeScript作成者の nderscore.js ライブラリも使用している場合、うまく機能する1つのライナーがあります。

a = _(a).reject (v)-> v is e

またはjs:

a = _(a).reject(function(v) { return v == e; });
4
georgedyer

CoffeescriptまたはjQueryを使用したクリーンなアプローチを求めていますが、最もクリーンなアプローチはVanilla javascriptメソッド filter を使用していることです。

array.filter(function (item) { return item !== match });

Coffeescriptではきれいに見えますが、これはまったく同じjavascriptに変換されるため、視覚的な違いのみを考慮し、coffeescriptの高度な機能は考慮しません。

array.filter (item) -> item isnt match

フィルターはレガシーブラウザーではサポートされていませんが、MozillaはECMA標準に準拠する polyfill を提供します。これは完全に安全なアプローチだと思います。古いブラウザを最新の標準に近づけるだけで、ポリフィルで新しい機能を発明していないからです。

特にjQueryまたはCoffeescriptのみのメソッドを探していた場合は申し訳ありませんが、クリーンなjavascriptのみのメソッドを知らなかったため、主にライブラリメソッドを求めていたと思います。

そこにライブラリがあります!

4
TimE

これは、 アミールの素晴らしいソリューション へのわずかな変更です。

Array::remove = (e) -> @splice(t,1)[0] if (t = @indexOf(e)) > -1

リストに要素がある場合は要素を返すので、次のようなことができます。

do_something 100 if a.remove(100)

コーヒーの除去スクリプトは、次のjavascriptに変換されます。

Array.prototype.remove = function(e) {
  var t, _ref;
  if ((t = this.indexOf(e)) > -1) {
    return ([].splice.apply(this, [t, t - t + 1].concat(_ref = [])), _ref);
  }};
3
Durant Schoon

JQueryのgrepユーティリティを試してみてください。

a = [4,8,2,3]
$.grep(a,function(v){return v!=8;})

ここでは、技術的に変数がnew配列を参照するようにしているため、パフォーマンスの問題がある可能性があります。あなたは実際に元のものを変更していません。オリジナルがどこか他の場所で参照されていないと仮定すると、ガベージコレクターはこれをかなり迅速に取得する必要があります。これは私にとって決して問題ではありませんでしたが、他の人はもっとよく知っているかもしれません。乾杯!

1
Mike Marcacci