views:

85

answers:

3
var arr = [foo,bar,xyz];
arr[arr.indexOf('bar')] = true;

Is there an easier way to do this in JS?

+1  A: 

All values in that array are already undefined. (You edited your post) I don't know why you are complaining about 2 whole lines of code though.

Short answer no, you can't access an index of an array without knowing the index.

One IE safe way would be to create a prototyped function which lets you set it easily:

Array.prototype.setKeysWithValue = function(keyValue,newValue)
    {
    var i;
    for (i in this)
        {
        if (this[i] === keyValue)
            this[i] = newValue;
        }
    }

This can then be used like:

var arr = ['foo','bar','xyz'];
arr.setKeysWithValue('bar',true);
Andrew Dunn
My bad. I just meant to ask if there's any way to refer to an Array element without knowing it's index apart from arr[arr.indexOf(something)]. I've updated the code; thanks.
tta
@Andrew - seeing as IE<9 doesn't have `.indexOf()` on arrays, it's not an invalid question, your answer is a little condescending, and uninformed. This should have been a comment if anything.
Nick Craver
Why are you posting answers that aren't answers? These should be comments.
Robert
Earlier it did answer the question, but the question was changed making me look more condescending.
Andrew Dunn
@Andrew - It was changed from `undefined` to `true`, I saw it as it was originally posted, and I don't see how that affects your answer any...
Nick Craver
Sorry, my bad...
Andrew Dunn
@Andrew - not my downvote, just trying to give some constructive criticism :)
Nick Craver
+3  A: 

You could just use objects.

var obj = {foo: true, baz: false, xyz: true};
obj.baz = true;
Louis
don't you mean `obj.baz = true`?
Andrew Dunn
That I do, son!
Louis
You should also note the `obj["baz"]` syntax, which is what I think the OP wants.
Yi Jiang
Well yeah I guess if you want. If the key you want to access is in a variable then `obj[mykey]` is helpful.
Louis
Actually I think the OP wants to get the index based on it's value, not the key name.
Andrew Dunn
A: 

In your example you would really only be replacing "bar" with true; your resultant array would look like [foo, true, xyz].

I think it's assumed that what you're asking for is an alternative to having one set of arrays for keys and one set of arrays for values, of which there is no better way.

However, you can use an associative array, or objects, to maintain a key value pair.

var f = false, t = true;

// associative array
var arr = new Array();
arr["foo"] = arr["bar"] = arr["foobar"] = f;
arr["bar"] = t;


// object
var obj;
obj = {"foo":f, "bar":f, "foobar":f};
obj["bar"] = t;

// the difference is seen when you set arr[0]=t and obj[0]=t
// the array still maintains it's array class, while the object
// is still a true object

It's important to realize a few things if you use this method:

  • the array.length no longer applies, as it only accounts arrays by numerical index, it does not count array properties, which is what the keys in an associative array are
  • looping through keys/properties becomes a little more difficult since the Array object should have some native properties/methods
  • you may only have one key/value pair. The array structure you listed would be allowed to have [foo, bar, xyz, bar, foobar, foo], where the index should return the first occurrence in anything browser other than IE<=8

One other way to do what you were specifically asking is:

   Array.prototype.replace    = function(from,to){ this[this.indexOf(from)]=to;                               };
   Array.prototype.replaceAll = function(from,to){ while(this.indexOf(from)>=0){this[this.indexOf(from)]=to;} };

   var arr = new Array();
   arr=[ "foo", "bar", "foobar", "foo" ];
   arr.replace("bar",true);              // [ "foo", true, "foobar", "foo" ]
   arr.replaceAll("foo",false);          // [ false, true, "foobar", false ]
vol7ron