Skip to content

Instantly share code, notes, and snippets.

@jed
Forked from 140bytes/LICENSE.txt
Created May 10, 2011 16:06
Show Gist options
  • Star 4 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save jed/964769 to your computer and use it in GitHub Desktop.
Save jed/964769 to your computer and use it in GitHub Desktop.
walk and filter DOM nodes by function
function d(
a, // a function to filter the node results (optional)
b, // the ancestor element to walk (optional, defaults to document)
c // placeholder for the result node list
){
b === c && // if b is undefined,
(b=document); // use the document
c = c || []; // intialize the node list if it doesn't exist
if (b) { // if the element exists
if ( // and
!a || a(b) // matches the filter function if one exists,
) c.push(b); // push it to the results.
d(a, b.firstChild, c); // repeat for the first child
d(a, b.nextSibling, c) // repeat for the next sibling
}
return c // return the results
}
function d(a,b,c){b===c&&(b=document);c||(c=[]);if(b){if(!a||a(b))c.push(b);d(a,b.firstChild,c);d(a,b.nextSibling,c)}return c}
DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE
Version 2, December 2004
Copyright (C) 2011 Jed Schmidt <http://jed.is>
Everyone is permitted to copy and distribute verbatim or modified
copies of this license document, and changing it is allowed as long
as the name is changed.
DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE
TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
0. You just DO WHAT THE FUCK YOU WANT TO.
{
"name": "walk",
"keywords": ["walk", "filter", "DOM"]
}
@kassens
Copy link

kassens commented May 22, 2011

c = c || []; could save you 2 byte.

@jed
Copy link
Author

jed commented May 23, 2011

Good catch, thanks!

@atk
Copy link

atk commented Jun 9, 2011

Same goes for "b = b || document" instead of "1 in arguments || b = document".

@jed
Copy link
Author

jed commented Jun 9, 2011

@atk this function is actually sensitive to arity, so this suggestion wouldn't work.

@atk
Copy link

atk commented Jun 10, 2011

Missed that. But I had another idea: why not a typesafe comparison with the uninitialized placeholder variable, e.g.

function d(a,b,c){b===c&&(b=document);c=c||[];

instead of the much longer

function d(a,b,c){c||(c=[]);1 in arguments||(b=document);

Regards, atk

@jed
Copy link
Author

jed commented Jun 10, 2011

that's a good call, @atk. changed!

@atk
Copy link

atk commented Jun 10, 2011

Thanks, @jed

@immaterialh
Copy link

Hiya, I just stumbled across this and think i spotted another shortcut (and just created an account to comment ;-) )
basically using ?: to avoid needing brackets in the ifs

b===c&&(b=document); to b=b===c?document:b; saves a character

if(b){if(!a||a(b))...} to b?(!a||a(b0?...:0)...:0 this saves 3 characters, but needs commas to change to +'s and repeatedly flattens & throws away the arrays, which makes it slower :-/

all together :
function d(a,b,c){b=b===c?document:b;c=c||[];b?(!a||a(b)?c.push(b):0)+d(a,b.firstChild,c)+d(a,b.nextSibling,c):0;return c}

and then using the returned arrays instead of referencing c
ie d(a,...,c)+d(a,...,c)
to d(a,...,d(a,...,c))
saves another 2 & stops the arrays getting flattened :-D
function d(a,b,c){b=b===c?document:b;c=c||[];b?(!a||a(b)?c.push(b):0)+d(a,b.firstChild,d(a,b.nextSibling,c)):0;return c}

and then putting (!a||a(b)?c.push(b):0) in an unused parameter

finally 118 characters
function d(a,b,c){b=b===c?document:b;c=c||[];b?d(a,b.firstChild,d(a,b.nextSibling,c,!a||a(b)?c.push(b):0)):0;return c}

@jpidelatorre
Copy link

Moving the assignment for c to the first point where it is needed saves 2 bytes:

// 116 bytes
function d(a,b,c){b=b===c?document:b;b?d(a,b.firstChild,d(a,b.nextSibling,c=c||[],!a||a(b)?c.push(b):0)):0;return c}

Switching the ternaries (except for the first one) for Boolean operations saves another 2:

// 114 bytes
function d(a,b,c){(b=b===c?document:b)&&d(a,b.firstChild,d(a,b.nextSibling,c=c||[],!a||a(b)&&c.push(b)));return c}

Moving the return to the front and bringing the ternary back saves 2 more:

// 112 bytes
function d(a,b,c){return(b=b===c?document:b)?d(a,b.firstChild,d(a,b.nextSibling,c=c||[],!a||a(b)&&c.push(b))):c}

And then, if you were allowed to, you could turn it into a slick arrow function saving 14 more bytes:

// 98 bytes
d=(a,b,c)=>(b=b===c?document:b)?d(a,b.firstChild,d(a,b.nextSibling,c=c||[],!a||a(b)&&c.push(b))):c

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment