Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > Javascript > can't do recursive function

Reply
Thread Tools

can't do recursive function

 
 
samuelberthelot@googlemail.com
Guest
Posts: n/a
 
      07-11-2006
Hi,
I'm trying to write a recursive fucntion that takes as parameters a
html div and an id. I have to recurse through all the children and
sub-children of the div and find the one that matches the id.
I have the following but it doesn't work well (algorighm issue) :

var cn = null;
function getChildElement(parent, childID){
for (var i=0; i<parent.childNodes.length; i++){
cn = parent.childNodes[i];
if(cn.getAttribute){

if(cn.getAttribute("id").toLowerCase().indexOf(chi ldID.toLowerCase()) >
-1 ){
return cn;
}else{
return getChildElement(parent.childNodes[i], childID);
}
}
}
return cn;
}


Can you help please ?

 
Reply With Quote
 
 
 
 
Vincent van Beveren
Guest
Posts: n/a
 
      07-11-2006
What goes wrong? Why are you doing this anyway, ID's in a page should be
unique, so document.getElementById() should always work. You can check
with element.parentNode whether its in the correct location:

function checkParent(elem, requiredParent) {
while (elem.parentNode != null) {
if (elem.parentNode == requiredParent) {
return true;
}
elem = elem.parentNode;
}
return false;
}

Anyway, just a thought. The alogirth, looks good to me. You can invoke
getChildElement(cn, childID) instead of parent.childNodes[i]. Do you
know what goes wrong? does it give an error?

Vincent
 
Reply With Quote
 
 
 
 
RobG
Guest
Posts: n/a
 
      07-12-2006
http://www.velocityreviews.com/forums/(E-Mail Removed) wrote:
> Hi,
> I'm trying to write a recursive fucntion that takes as parameters a
> html div and an id. I have to recurse through all the children and
> sub-children of the div and find the one that matches the id.
> I have the following but it doesn't work well (algorighm issue) :
>
> var cn = null;


You don't need cn as a global, you can keep it local.


> function getChildElement(parent, childID){


var cn;

> for (var i=0; i<parent.childNodes.length; i++){


It is more efficient to get the length of childNodes once and use that,
there might be lots of them!

for (var i=0; len<parent.childNodes.length; i<len; i++){

You could also use a while loop, the following goes backwards through
the nodes (which shouldn't be an issue here):

var i = parent.childNodes.length
while (i--) {


> cn = parent.childNodes[i];
> if(cn.getAttribute){
>
> if(cn.getAttribute("id").toLowerCase().indexOf(chi ldID.toLowerCase()) >
> -1 ){


A slightly simpler test (to me at least) is:

if (cn.id && cn.id.toLowerCase() == childID.toLowerCase()){


> return cn;


So far so good, this will traverse all the child nodes and return a
match if one is found.

> }else{


The above if will return if true and the function ends, so there is no
need for 'else'.


> return getChildElement(parent.childNodes[i], childID);


But here you get into trouble. Firstly, 'cn' already refers to
parent.childNodes[i] so use it.

Next, as a speed optimisation, only call getChildElement if cn has
children:

if (cn.childNodes){


It should be quicker to test here than create a new recursive function
object and test it there.

Next, when you recursively call getChildElement, the result will be
returned to the spot it was called from. Your code returns whatever
the call returns immediately, without testing. Have getChildElement
return either an element, or something that evaluates to false. If you
get an element, it must be a match, so return it (and so on back up the
recursion chain...).

If you don't get an element, don't return, let the loop continue.
Something like:

var x = getChildElement(cn, childID);
if (x) return x;
}


> }
> }
> }
> return cn;


At this point you should return something that will evaluate to false
in an if test. You can explicitly return false if you like, but you
could do it by inference by returning nothing. That will result in the
function returning 'undefined' if no element is returned, and hence x
will be false in the test above - it depends on your coding standards
and preferences.

> }


I get the feeling I'm doing your homework, so I'll leave pasting the
bits together to you.

--
Rob

 
Reply With Quote
 
RobG
Guest
Posts: n/a
 
      07-12-2006

RobG wrote:
[...]
> It is more efficient to get the length of childNodes once and use that,
> there might be lots of them!
>
> for (var i=0; len<parent.childNodes.length; i<len; i++){


Gosh, that's ugly...

for (var i=0, len=parent.childNodes.length; i<len; i++){

[...]

--
Rob

 
Reply With Quote
 
 
 
Reply

Thread Tools

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
function returning function pointer (recursive type) Mark Piffer C Programming 9 05-15-2009 07:54 AM
Recursive functions Vs Non-recursive functions - performance aspect vamsi C Programming 21 03-09-2009 10:53 PM
Two recursive calls inside of a recursive function n00m C++ 12 03-13-2008 03:18 PM
defined? for recursive function call v/s defined? for function call stack Alok Ruby 3 04-13-2006 11:53 AM
write a function such that when ever i call this function in some other function .it should give me tha data type and value of calling function parameter komal C++ 6 01-25-2005 11:13 AM



Advertisments