...

View Full Version : Find In Array



subha rr
05-23-2009, 10:44 AM
Hi.....

To find whether given value is present in an array or not. Enter the value into textbox and find whether the given value is found in array or not....

How to write code in javascript

Pls help me

Regards
Subha

abduraooft
05-23-2009, 10:48 AM
Refer https://developer.mozilla.org/En/Core_JavaScript_1.5_Reference:Objects:Array:indexOf (thoroughly...)

subha rr
05-23-2009, 12:46 PM
Refer https://developer.mozilla.org/En/Cor...:Array:indexOf (thoroughly...)

This link is very usefull

Thank u very much

rnd me
05-23-2009, 11:53 PM
if you are looking for a String, and care about performance, here is fast and simple cross-browser function:



var names=["dan", "sharon", "bob", "fred", "sally"];

function inArray(ray, str){
return ("|"+ ray.join("|") +"|" ).indexOf("|"+str+"|")!==-1;
}

// Examples:
inArray(names, "fred")//true
inArray(names, "fre")//false
inArray(names, "Sally")//false
inArray(names, "sally")//true


if you want to find sub-matches, remove all the "|" additions to each side...

this is going to be a lot faster than a loop-based [].indexOf replacement in non-firefox browsers.

Philip M
05-24-2009, 10:45 AM
if you are looking for a String, and care about performance, here is fast and simple cross-browser function:



var names=["dan", "sharon", "bob", "fred", "sally"];

function inArray(ray, str){
return ("|"+ ray.join("|") +"|" ).indexOf("|"+str+"|")!==-1;
}

// Examples:
inArray(names, "fred")//true
inArray(names, "fre")//false
inArray(names, "Sally")//false
inArray(names, "sally")//true


Can you explain how the index of a match can be returned rather than simply true or false? I do appreciate that the OP requested "...and find whether the given value is found in array or not...."

rnd me
05-25-2009, 01:09 AM
Can you explain how the index of a match can be returned rather than simply true or false? I do appreciate that the OP requested "...and find whether the given value is found in array or not...."

that information must come at the cost of a slower construct like a loop or RegExp. You might be able to use the joined match index, the length of the array, and a slice of joined match to find this.
It would probably be easier to use Array.indexOf at that point and let IE users suffer themselves.

Philip M
05-25-2009, 08:32 AM
that information must come at the cost of a slower construct like a loop or RegExp. You might be able to use the joined match index, the length of the array, and a slice of joined match to find this.
It would probably be easier to use Array.indexOf at that point and let IE users suffer themselves.

I have to say that unless the array is huge a loop or regex ought to be perfectly satisfactory, with the added advantage of being able to ignore case in the match. The odd millisecond or two is of no consequence.

I believe that IE still has 70% of the market, so something which does not work in IE is hardly useable.

fside
05-26-2009, 12:56 AM
Hi.....

To find whether given value is present in an array or not. Enter the value into textbox and find whether the given value is found in array or not....

How to write code in javascript

Pls help me

Regards
Subha

Value in the more generic CS sense to mean 'whatever's in the box' or value meaning a scalar value?

Either way, sort. You could use a binary search (very easy to do). If you can use built-in javascript methods, those will always be much faster.

I suppose if you know it's a small array, you could just .join(","), prefix and suffix the resulting string with commas, and use indexOf to find the values between two commas - if it's simply a matter of detecting potential duplicates rather than array position. Small array though.

Firefox should have array.filter(), where filter runs a function you name. Returns all true instances as an array. But not IE7, which you mentioned (you could prototype the Array object with a function running a loop - but . . ?).

Old Pedant
05-26-2009, 01:13 AM
I think that rnd_me is missing the fact that join is *not* a zero-cost operation. The JS runtime must allocate a stringbuffer, append each of the strings of the array, then convert the stringbuffer to a string, just so that you can use indexOf.

Granted, if this is all being done by a library routine, it will be faster than the same steps in JS, but it's still a pretty lengthy process. And at the end, you still have to use indexOf( ) which is going to be slower than an equals comparison. Seems to me that a loop on the array, using == on each element, is probably going to be close to the same speed, and may even win out.

Might be fun to benchmark this one.

Note the original question:
Enter the value into textbox and find whether the given value is found in array or not....
So we *are* talking about a string value and we *are* talking about == matches.

Old Pedant
05-26-2009, 01:36 AM
Here's my test page:


<html><head>
<script>
var theArray = new Array(
"aardvark", "bear", "cougar", "deer", "elephant",
"fox", "goose", "horse", "ibex", "jaguar",
"koala", "lion", "moose", "nene", "owl",
"pigeon", "quail", "rooster", "stork", "tanager" );

function findViaJoin( what, inWhat )
{
return ("|" + inWhat.join("|") + "|").indexOf("|" + what + "|") != -1;
}
function findViaLoop( what, inWhat )
{
for ( var i = 0; i < inWhat.length; ++i )
{
if ( inWhat[i] == what ) return true;
}
return false;
}

function runTests( label, what )
{
var startAt = new Date();
for ( var count = 1; count < 50000; ++count )
{
findViaJoin( what, theArray );
}
var endAt = new Date();
document.write( label + " via join: " + (endAt.getTime()-startAt.getTime()) + "<hr>" );

var startAt = new Date();
for ( var count = 1; count < 50000; ++count )
{
findViaLoop( what, theArray );
}
var endAt = new Date();
document.write( label + " via loop: " + (endAt.getTime()-startAt.getTime()) + "<hr>" );
}
</script>
</head>
<body>
<script>
runTests( "find first item", "aardvark" );

runTests( "find last item", "tanager" );

runTests( "item not found", "zamboni" );
</script>
</body>
</html>


Here are the results of running it in MSIE 6 on my somewhat ancient Athlon 2600 machine (repeated runs gave results within 5% of these numbers):


find first item via join: 1152
--------------------------------------------------------------------------------
find first item via loop: 200
--------------------------------------------------------------------------------
find last item via join: 1252
--------------------------------------------------------------------------------
find last item via loop: 1242
--------------------------------------------------------------------------------
item not found via join: 1242
--------------------------------------------------------------------------------
item not found via loop: 1282
--------------------------------------------------------------------------------

Okay, so clearly the loop wins out in the average "found" case. The "join" wins out in the "not found" case.

That's on MSIE 6, though.

Here are the times with FF 3 !!


find first item via join: 983
--------------------------------------------------------------------------------
find first item via loop: 41
--------------------------------------------------------------------------------
find last item via join: 955
--------------------------------------------------------------------------------
find last item via loop: 462
--------------------------------------------------------------------------------
item not found via join: 990
--------------------------------------------------------------------------------
item not found via loop: 374
--------------------------------------------------------------------------------


Enough said???

Sometimes K.I.S.S. really is the best advice.

Old Pedant
05-26-2009, 01:46 AM
And a note to fside: Would you care to show any implementation where doing a sort( ) before the search is guaranteed to be faster, if it is even EVER faster???

A simple linear search through the elements of an array is guaranteed to be Order N (actually, N is the upper limit, but we still call that Order N).

The best sorts you can find are Order (N Log N). When you combine that with the cost of a binary search--which is Order Log N, you end up with Order LogN (N + 1). Which can't possibly compare to the simple linear search.

Granted, *IF* you are going to be searching in the array many times (specifically, more than Log N times) *then* doing the sort first followed by a binary search each time may well be faster. But how many times, in reality, have you seen such a scenario?

rnd me
05-26-2009, 09:37 AM
Sometimes K.I.S.S. really is the best advice.


first off, thank you Old Pedant for getting involved, and taking the time to put ideas to test.

i like open dialog and think that several coders putting effort into something is a great way to learn and optimize code. I remember the getElementsByClassName thread, and by the time we were done, we had a pretty good function.

thanks for taking the time to whip this up.
i like it, even if it didn't confirm my hypothesis.

_______________

while "join is *not* a zero-cost operation", it can be faster than loops, which are terrible in IE.

I think IE7 is more common and thus more important. Firefox has better performance no matter what, so tweaking is not worth it. But for IE, minor things can have a big impact.


I also noticed what i would consider a small bug in the code: if i was looking for 0, i might find "", false, null, etc...

adding the fix and tweaking the code yielded some significant performance improvements.

I found different results than what you posted, more in line with my original hunch.


I made the workload bigger, and cut down the # of rep, since IE wouldn't let me do very many on the big array.

the array is of the 1000 most common English words in print.

i also switched it to allow an on-demand test, also to allow more work per test in IE before it complained, ruining the timing.


Results (P4/winxp):
(loop2 is a version with my changes)

IE7:
find first item via join: 391
find first item via loop2: 0
find first item via loop: 0
find last item via join: 469
find last item via loop2: 531
find last item via loop: 719
item not found via join: 437
item not found via loop2: 547
item not found via loop: 1000


FF3:
find first item via join: 356
find first item via loop2: 1
find first item via loop: 1
find last item via join: 356
find last item via loop2: 130
find last item via loop: 132
item not found via join: 597
item not found via loop2: 132
item not found via loop: 138


FF3 [].indexOf():
find first item via indexOf: 1
find last item via indexOf: 28
item not found via indexOf: 30


so, in IE, the join version is 50% faster for the last item, and twice as fast for a not found. and Infinity slower for the first thing.

i don't know if you could conclude an average position for a given result in the array. if it's sometimes not there, it would be between 0 and 1000 ms in the conditions above. the join is predictable, and always takes about the same amount of time, while the loop varies wildly by hit positions. interesting stuff indeed.

i would suspect that most things would be found, and that the loop would usually be faster.

The upgraded loop version i posted comes close to my join trick on worst cases, and spanks it on best cases, so i would recommend it in all but the most predictable conditions.

for reference, i threw in test run using Array.indexOf in FF3, so IE users can see what they are missing.

I found it interesting how little difference traditional "performance tweaks" seems to make in FF3, almost like the browser tweaks it for you...


my conclusion
All web developers: please, use a Array.indexOf replacement, with the IE optimizations. That way, real surfers get there instantly, and IE users get there ASAP. thanks.




here is the test document i used:


<html><head>

</head>
<body>

Run Test:
<a href="javascript:runTests( 'find first item', 'a' ); ">first: a</a>
<a href="javascript:runTests( 'find last item', 'yourself' ); ">last: yourself</a>
<a href="javascript:runTests( 'item not found', 'zamboni'); " >none: zamboni</a>

<hr />

<div id='log'>

</div>
<script>
var theArray = ['a', 'ability', 'able', 'about', 'above', 'accept', 'access', 'according', 'account', 'achieve', 'across', 'act', 'action', 'activity', 'actually', 'add', 'addition', 'admit', 'advantage', 'advice', 'affair', 'affect', 'after', 'again', 'against', 'age', 'ago', 'agree', 'agreement', 'air', 'all', 'allow', 'almost', 'along', 'already', 'also', 'although', 'always', 'among', 'amount', 'an', 'analysis', 'and', 'animal', 'announce', 'another', 'answer', 'any', 'anyone', 'anything', 'anyway', 'appear', 'application', 'apply', 'approach', 'appropriate', 'area', 'argue', 'argument', 'arm', 'army', 'around', 'arrive', 'art', 'as', 'ask', 'aspect', 'association', 'assume', 'at', 'attempt', 'attention', 'attitude', 'authority', 'available', 'avoid', 'award', 'aware', 'away', 'baby', 'back', 'bad', 'bank', 'base', 'basic', 'basis', 'be', 'bear', 'because', 'become', 'bed', 'before', 'begin', 'behaviour', 'behind', 'believe', 'benefit', 'better', 'between', 'beyond', 'big', 'bill', 'bit', 'black', 'blood', 'board', 'body', 'book', 'both', 'box', 'boy', 'break', 'bring', 'brother', 'build', 'building', 'business', 'but', 'buy', 'by', 'call', 'campaign', 'can', 'capital', 'car', 'care', 'carry', 'case', 'catch', 'cause', 'cell', 'central', 'centre', 'century', 'certain', 'certainly', 'chance', 'change', 'chapter', 'character', 'charge', 'child', 'choice', 'choose', 'church', 'circumstance', 'city', 'claim', 'class', 'clear', 'clearly', 'client', 'close', 'club', 'colour', 'come', 'commission', 'committee', 'common', 'community', 'company', 'compare', 'competition', 'computer', 'concern', 'concerned', 'condition', 'conference', 'consider', 'contain', 'continue', 'contract', 'control', 'cos', 'cost', 'could', 'council', 'country', 'couple', 'course', 'court', 'cover', 'create', 'culture', 'cup', 'current', 'customer', 'cut', 'dark', 'data', 'date', 'daughter', 'day', 'dead', 'deal', 'death', 'decide', 'decision', 'defence', 'degree', 'demand', 'department', 'depend', 'describe', 'design', 'despite', 'detail', 'determine', 'develop', 'development', 'die', 'difference', 'different', 'difficult', 'difficulty', 'direction', 'director', 'discover', 'discuss', 'discussion', 'disease', 'division', 'do', 'doctor', 'dog', 'door', 'doubt', 'down', 'draw', 'drive', 'drop', 'due', 'during', 'duty', 'each', 'early', 'easy', 'eat', 'economic', 'economy', 'education', 'effect', 'effort', 'either', 'election', 'element', 'else', 'encourage', 'end', 'energy', 'enjoy', 'enough', 'ensure', 'enter', 'environment', 'especially', 'establish', 'even', 'evening', 'event', 'ever', 'every', 'everyone', 'everything', 'evidence', 'exactly', 'example', 'exist', 'expect', 'experience', 'explain', 'express', 'eye', 'face', 'fact', 'factor', 'fail', 'fall', 'family', 'far', 'father', 'feature', 'feel', 'feeling', 'few', 'field', 'fight', 'figure', 'fill', 'film', 'final', 'finally', 'financial', 'find', 'fine', 'finish', 'fire', 'firm', 'floor', 'fly', 'follow', 'following', 'food', 'foot', 'for', 'force', 'foreign', 'forget', 'form', 'former', 'forward', 'free', 'friend', 'from', 'front', 'full', 'function', 'fund', 'further', 'future', 'game', 'garden', 'general', 'generally', 'get', 'girl', 'give', 'glass', 'go', 'goal', 'good', 'government', 'great', 'ground', 'group', 'grow', 'growth', 'hair', 'half', 'hand', 'happen', 'happy', 'hard', 'have', 'he', 'head', 'health', 'hear', 'heart', 'heavy', 'help', 'her', 'here', 'herself', 'high', 'him', 'himself', 'his', 'history', 'hit', 'hold', 'home', 'hope', 'horse', 'hospital', 'hotel', 'hour', 'house', 'how', 'however', 'human', 'husband', 'i', 'idea', 'identify', 'if', 'image', 'important', 'improve', 'in', 'include', 'including', 'income', 'increase', 'indeed', 'indicate', 'individual', 'industrial', 'industry', 'information', 'instance', 'instead', 'institution', 'intend', 'interest', 'international', 'into', 'introduce', 'investment', 'involve', 'issue', 'it', 'item', 'its', 'itself', 'job', 'join', 'just', 'keep', 'kill', 'kind', 'king', 'know', 'knowledge', 'labour', 'land', 'language', 'large', 'last', 'late', 'later', 'law', 'lead', 'leader', 'learn', 'least', 'leave', 'left', 'leg', 'legal', 'less', 'let', 'letter', 'level', 'library', 'lie', 'life', 'light', 'like', 'likely', 'line', 'list', 'listen', 'little', 'live', 'local', 'long', 'look', 'lose', 'loss', 'lot', 'love', 'low', 'machine', 'main', 'maintain', 'major', 'majority', 'make', 'man', 'manage', 'management', 'manager', 'many', 'market', 'material', 'matter', 'may', 'maybe', 'me', 'mean', 'means', 'measure', 'meet', 'meeting', 'member', 'memory', 'mention', 'method', 'might', 'mile', 'military', 'mind', 'minister', 'minute', 'miss', 'model', 'modern', 'moment', 'money', 'month', 'more', 'morning', 'most', 'mother', 'move', 'movement', 'much', 'music', 'must', 'my', 'myself', 'name', 'national', 'natural', 'nature', 'near', 'nearly', 'necessary', 'need', 'never', 'new', 'news', 'next', 'nice', 'night', 'no', 'nor', 'normal', 'not', 'note', 'nothing', 'now', 'number', 'obtain', 'obviously', 'occur', 'of', 'off', 'offer', 'office', 'officer', 'often', 'oil', 'okay', 'old', 'on', 'once', 'one', 'only', 'open', 'operate', 'operation', 'opportunity', 'or', 'order', 'organisation', 'original', 'other', 'our', 'out', 'outside', 'over', 'own', 'page', 'paper', 'parent', 'part', 'particular', 'particularly', 'party', 'pass', 'patient', 'pattern', 'pay', 'people', 'per', 'percent', 'performance', 'perhaps', 'period', 'person', 'personal', 'pick', 'picture', 'piece', 'place', 'plan', 'plant', 'play', 'player', 'please', 'point', 'police', 'policy', 'political', 'poor', 'popular', 'population', 'position', 'possible', 'pound', 'power', 'practice', 'prepare', 'present', 'president', 'press', 'pressure', 'prevent', 'previous', 'price', 'prime', 'principle', 'private', 'probably', 'problem', 'procedure', 'process', 'produce', 'product', 'production', 'professional', 'profit', 'programme', 'project', 'property', 'proposal', 'prove', 'provide', 'provision', 'public', 'publish', 'pull', 'pupil', 'purpose', 'put', 'quality', 'question', 'quickly', 'quite', 'raise', 'range', 'rate', 'rather', 'reach', 'read', 'ready', 'real', 'really', 'reason', 'receive', 'recent', 'recently', 'record', 'red', 'reduce', 'refer', 'reflect', 'refuse', 'region', 'relate', 'relation', 'relationship', 'remain', 'remember', 'remove', 'replace', 'report', 'represent', 'require', 'research', 'resource', 'respect', 'response', 'responsibility', 'rest', 'result', 'return', 'reveal', 'right', 'rise', 'risk', 'road', 'role', 'room', 'round', 'royal', 'rule', 'run', 'sale', 'same', 'save', 'say', 'scheme', 'school', 'science', 'sea', 'season', 'seat', 'secretary', 'section', 'sector', 'security', 'see', 'seek', 'seem', 'sell', 'send', 'sense', 'series', 'serious', 'serve', 'service', 'set', 'several', 'shall', 'share', 'she', 'shop', 'short', 'should', 'show', 'side', 'sign', 'significant', 'similar', 'simple', 'simply', 'since', 'single', 'sit', 'site', 'situation', 'size', 'skill', 'small', 'smile', 'so', 'social', 'society', 'some', 'someone', 'something', 'sometimes', 'son', 'soon', 'sorry', 'sort', 'sound', 'source', 'space', 'speak', 'special', 'specific', 'spend', 'staff', 'stage', 'stand', 'standard', 'start', 'state', 'statement', 'station', 'stay', 'step', 'still', 'stone', 'stop', 'story', 'street', 'strong', 'structure', 'student', 'study', 'style', 'subject', 'success', 'successful', 'such', 'suddenly', 'suffer', 'suggest', 'summer', 'support', 'suppose', 'sure', 'surface', 'system', 'table', 'take', 'talk', 'task', 'tax', 'teach', 'teacher', 'team', 'technique', 'technology', 'tell', 'tend', 'term', 'test', 'than', 'thank', 'that', 'the', 'their', 'them', 'themselves', 'then', 'theory', 'there', 'therefore', 'these', 'they', 'thing', 'think', 'this', 'those', 'though', 'thought', 'through', 'throughout', 'throw', 'thus', 'time', 'title', 'to', 'today', 'together', 'too', 'top', 'total', 'towards', 'town', 'trade', 'train', 'training', 'treat', 'treatment', 'tree', 'TRUE', 'try', 'turn', 'type', 'under', 'understand', 'union', 'unit', 'university', 'unless', 'until', 'up', 'upon', 'us', 'use', 'used', 'useful', 'user', 'usually', 'value', 'variety', 'various', 'version', 'very', 'view', 'village', 'visit', 'voice', 'wait', 'walk', 'wall', 'want', 'war', 'watch', 'water', 'way', 'we', 'wear', 'week', 'well', 'what', 'whatever', 'when', 'where', 'whether', 'which', 'while', 'white', 'who', 'whole', 'whom', 'whose', 'why', 'wide', 'wife', 'will', 'win', 'window', 'wish', 'with', 'within', 'without', 'woman', 'wonder', 'word', 'work', 'worker', 'world', 'would', 'write', 'wrong', 'yeah', 'year', 'yes', 'yesterday', 'yet', 'you', 'young', 'your', 'yourself'];

function findViaJoin( what, inWhat )
{
return ("|" + inWhat.join("|") + "|").indexOf("|" + what + "|") !== -1;
}

function findViaLoop( what, inWhat )
{
for ( var i = 0; i < inWhat.length; ++i )
{
if ( inWhat[i] == what ) return true;
}
return false;
}

function findViaLoop2( what, inWhat ){

for ( var i = 0, mx=inWhat.length; i < mx; i++ ){
if ( inWhat[i] === what ) {return true};
}
return false;
}


function findViaSort( what, inWhat ){
var result=false;
var hit=function(a,b){ if(a===what){result=true;} return 0; }
inWhat.sort(hit);
return result;
}



function runTests( label, what )
{
var startAt = new Date();
for ( var count = 1; count < 1000; ++count )
{
findViaJoin( what, theArray );
}
var endAt = new Date();
document_write( label + " via join: " + (endAt.getTime()-startAt.getTime()) + "<hr>" );


var startAt = new Date();
for ( var count = 1; count < 1000; ++count )
{
findViaLoop2( what, theArray );
}
var endAt = new Date();
document_write( label + " via loop2: " + (endAt.getTime()-startAt.getTime()) + "<hr>" );




var startAt = new Date();
for ( var count = 1; count < 1000; ++count )
{
findViaLoop( what, theArray );
}
var endAt = new Date();
document_write( label + " via loop: " + (endAt.getTime()-startAt.getTime()) + "<hr>" );
}


var log= document.getElementById("log");

function document_write(str){
log.innerHTML= log.innerHTML+str;
}

</script>

</body>
</html>

Philip M
05-26-2009, 10:41 AM
Most interesting. I am reminded of the old country saying:-

"When oak and ash are out in May
It don't prove nothing, either way". :D

Seriously, is there any meaningful difference between 469 and 531 ms?
There will be far greater variations in the speed with which the user types the word to be matched (or not).

rnd me
05-26-2009, 12:13 PM
Seriously, is there any meaningful difference between 469 and 531 ms?
There will be far greater variations in the speed with which the user types the word to be matched (or not).



The upgraded loop version i posted comes close to my join trick on worst cases, and spanks it on best cases, so i would recommend it in all but the most predictable conditions.

unless you are expecting lots of misses, use the ie optimized loop.

to reiterate and facilitate those who like to cut and paste,
always use this:


if(![].indexOf){ Array.prototype.indexOf=function(what){
for ( var i=0, mx=this.length;i<mx;i++){
if(inWhat[i]===what || inWhat[i++]===what){return true};
}
return -1;
}} //end [].indexOf

then, your custom function would be much simpler:




var names=["dan", "sharon", "bob", "fred", "sally"];


function inArray(ray, str){
return ray.indexOf(str)!==-1;
}

// Examples:
inArray(names, "fred")//true
inArray(names, "fre")//false
inArray(names, "Sally")//false
inArray(names, "sally")//true


that should test about the same as the loop2 test-case in IE, and close to the [].indexOf test-case in FF3+ safari.

Philip M
05-26-2009, 12:41 PM
I am not carping, but surely in most situations a case insensitive match is required?

Sally matches sally.

rnd me
05-26-2009, 01:57 PM
I am not carping, but surely in most situations a case insensitive match is required?

Sally matches sally.




if(![].filter){Array.prototype.filter=function(f,x){var t=this,m=t.length,r=[],i=0,v;
for(;i<m;i++){if(i in t){v=t[i];if(f.call(x,v,i,t)){r.push(v);}}}return r;};
}

var names=["dan", "sharon", "bob", "fred", "sally"];

function finder(a){return String(a).toLowerCase()==this; }

function inArray(ray, str){
return ray.filter(finder ,str.toLowerCase()).length >0;
}

// Examples:
inArray(names, "fred")//true
inArray(names, "fre")//false
inArray(names, "Sally")//true
inArray(names, "sally")//true


this also brings up one possible advantage to a join version: you could convert the whole thing at once to lowerCase...
might change the performance standings a bit, but i like filter for simplicity and flexibility.
[].filter also gathers all the results, and you can easily change finder to gather partial hits, which would be good for suggestions.

Old Pedant
05-26-2009, 09:53 PM
I'm sorry, I don't understand how this code works:


if(![].indexOf){ Array.prototype.indexOf=function(what){
for ( var i=0, mx=this.length;i<mx;i++){
if(inWhat[i]===what || inWhat[i++]===what){return true};
}
return -1;
}} //end [].indexOf

(1) It returns true when a match is found, -1 when it's not. But -1 when considered as a boolean value *is* true. So, in essence, this always returns true.
(2) What is the point of this code:


if(inWhat[i]===what || inWhat[i++]===what)
????
If variable i contains (example) 6, then the first comparison checks inWhat[6] and leaves i at 6. If that fails, the second comparison *AGAIN* checks inWhat[6] but then bumps i to 7 *after* the comparison. Since the first comparison failed, the second comparison will of necessity also fail. But now i has been bumped from 6 to 7. And then the for( ) loop will *also* bump i, now from 7 to 8. And you NEVER CHECK the value of inWhat[7] !!!

In short, your loop never tests for any of the odd numbered values in the array.

*IF* you had coded

if(inWhat[i]===what || inWhat[++i]===what)
then the code makes more sense. But, still, now you *might* be checking a non-existent array element if i exceeds the upper bound of the array, which will happen whenever there are an odd number of elements in the array and the element is not found.

Quibbling, I know. But...

Your use of === in place of == makes me a little nervous. One could imagine a novice storing an array of integer values and then looking in that array for a value that is coming form a form fields ".value". The .value is a string, so of course there will never be a match. Yes, yes, I know: caveat emptor, or something like that.

rnd me
05-27-2009, 03:49 AM
I'm sorry, I don't understand how this code works:
In short, your loop never tests for any of the odd numbered values in the array.



Yikes! That's what i get for coding without sleep.

The reason it's there is performance.
a single extra check yields at least 10% better IE7 performance in my tests.



if(![].indexOf){ Array.prototype.indexOf=function(what){
for ( var i=0, mx=this.length;i<mx; i=i++){
if(inWhat[i]===what || inWhat[++i]===what){return i;};
}
return -1;
}} //end [].indexOf



it's a shorthanded loop fold, two array elements per loop;

going over the last index would simply evaluate to undefined.
unless you are trying to find undefined, going over wont hurt a bit.
It's no big deal, and certainly not worth a conditional to prevent.
If you tried to add two in the loop init (i,i<mx,i+=2), you might miss the last array element.


i originally had several fallbacks, so i++ was fine for the version i didn't post.




Your use of === in place of == makes me a little nervous. One could imagine a novice storing an array of integer values and then looking in that array for a value that is coming form a form fields ".value". The .value is a string, so of course there will never be a match. Yes, yes, I know: caveat emptor, or something like that.
When applying a prototype with the same name as a function in another browser, it is critical that you mimic the existing behavior exactly.
Without ===, it would be impossible to differentiate between NaN and 0 in the aforementioned array of integers...

If you have [].map in-place, type-casting an entire array is trivial:

var ray2=ray.map(String); would turn the array of numbers into strings.

note that the second version i posted (post #16), does not suffer the [].indexOf drawback you point out, since the filter function explicitly calls String before comparing the result to needle.

thanks for the heads up, and sorry about the buggy code.

Old Pedant
05-27-2009, 03:59 AM
whew. Thought maybe I'd missed something big.

I figured it was for performance, though I'm surprised it made that much difference.

But if you are going to make two tests per loop iteration, why not three or four or...??

Is there a point of diminishing returns??

Ehhh...don't go test it out. I think we've beat this dead horse way more than it deserved. It's fun stuff, but in reality I think it will never matter. When you have to do thousands of iterations to make something measurable, it's hard to think that the thing being measured can really matter. Not like we are writing server-side code here. <grin/>

rnd me
05-27-2009, 04:07 AM
But if you are going to make two tests per loop iteration, why not three or four or...??

Is there a point of diminishing returns??


yes. four fallbacks was about 5% faster than one fallback.

it's worth the extra little bit for bonus 10%.

beyond that, no, not to me.

that would mean that i would have to wait for extra code to download instead of some IE user waiting a bit longer to execute it.
not on my watch.



EZ Archive Ads Plugin for vBulletin Copyright 2006 Computer Help Forum