473,394 Members | 1,781 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

Join Bytes to post your question to a community of 473,394 software developers and data experts.

Document nodes returning null

Im writing some Javascript code that requires me to loop all child nodes and sub child nodes of a certain parent node and execute a function with the child node in question.

I decided to write a recursive function with said functionality, with a node and a function as parameters, but it simply wont work.

My problem is that whenever i pass a node to this function parameter it is always, regardless of what i change, equal to null. I even modified my custom passed function to ignore null nodes, and now it throw a null variable error every time my function recurses.
(exact error: node.childNodes has no properties)

To me it looks like a problem with these infamous 'closures' i keep hearing about. I understand the concept, but I dont know exactly how they work in this context due to a great lack of experience :(.

I know there are many sample codes out there that can do the job, but I want to know why THIS function, which looks perfectly logical to me, doesnt behave as i would expect it too.

I read a few posts here and there relating to this, and I modified my code accordingly, but i cant seem to figure out just what is causing my problem.

Expand|Select|Wrap|Line Numbers
  1. var ProcNodes=function(node,fn)
  2. {
  3.     var n=0,
  4.         i=0,
  5.         nodes=node.childNodes,
  6.         length=nodes.length;
  7.     for(i=0;i<length;i++)
  8.     {
  9.         var node=nodes[i];
  10.         fn.call(node);
  11.         if(node.childNodes.length>0)
  12.             n+=ProcNodes(fn,node);
  13.         n++;
  14.     }
  15.     return n;
  16. }
thx in advance,
Yoann Arseneau
Nov 20 '07 #1
14 1987
gits
5,390 Expert Mod 4TB
hi ...

welcome to TSDN ...

i fixed your code ... have a close look at the example ... i tested it with google.com in firebug and it worked:

Expand|Select|Wrap|Line Numbers
  1. var ProcNodes = function(node, fn) {
  2.     var nodes  = node.childNodes;
  3.     var length = nodes.length;
  4.  
  5.     for (var i = 0 ; i < length; i++) {
  6.         var node = nodes[i];
  7.  
  8.         fn.call(node);
  9.  
  10.         if (node.childNodes.length > 0) {
  11.             ProcNodes(node, fn);
  12.         }
  13.      }   
  14. }
  15.  
  16. ProcNodes(document.getElementsByTagName('body')[0], function() {
  17.     alert(this.nodeType);
  18. });
  19.  
we don't need the n and i fixed the order of params in the recursion call

kind regards
Nov 20 '07 #2
heh... well im kinda embarrassed :\

thx for your help XD
Nov 20 '07 #3
mrhoo
428 256MB
Excuse this- I missed gits post.

Expand|Select|Wrap|Line Numbers
  1. nodecall= function(node,fun){
  2.     var n= [],tem;    
  3.     tem= node.firstChild;
  4.     while(tem){        
  5.         n.push(fun.call(tem));
  6.         if(tem.hasChildNodes()) n.push(arguments.callee(tem,fun));
  7.         tem= tem.nextSibling;        
  8.     }
  9.     return n;
  10. }
Expand|Select|Wrap|Line Numbers
  1. function ahoy(){
  2.     return this.nodeName;
  3. }
var A=nodecall(document.body,ahoy);
alert(A.join('\n\n'));
Nov 20 '07 #4
gits
5,390 Expert Mod 4TB
heh... well im kinda embarrassed :\

thx for your help XD
hi ...

no problem ... post back to the forum anytime you have more questions ...

kind regards
Nov 20 '07 #5
Im still getting some null nodes, but i think i just figured it out.

From what i can tell, firefox (browser im currently testing on) returns whitespace textnodes as null objects.

Can someone confirm this so i can finally stop worrying about this insignificant part of my app :\
Nov 20 '07 #6
gits
5,390 Expert Mod 4TB
it returns them as textnodes ... nodeType == 3 or nodeName == '#text' ... so with that you may handle them ... could tell where you get a null-value?
Nov 20 '07 #7
Expand|Select|Wrap|Line Numbers
  1. if(node==null)
  2. {
  3.     alert("ParseNode: null node");
  4.     return;
  5. }
this message alerts several times during my loop, it is the first statement inside my calling function (fn parameter)

<EDIT>
the node variable is the one directly passed from the recursive function
Nov 20 '07 #8
gits
5,390 Expert Mod 4TB
hmmm ... that is strange ... could you post your html ... i think in case of a text node it should alert a '[object Text]' ...
Nov 20 '07 #9
Well this is prety wierd... When i changed the statement on line 7 my script suddenly started acting exactly like expected.

Expand|Select|Wrap|Line Numbers
  1. var ProcNodes=function(node,fn)
  2. {
  3.     var nodes=node.childNodes,length=nodes.length,n=0;
  4.     for(var i=0;i<length;i++)
  5.     {
  6.         var node=nodes[i];
  7.         if(!fn(node))// was previously fn.call(node)
  8.             return-n;
  9.         if(node.childNodes.length>0)
  10.             n+=ProcNodes(node,fn);
  11.         n++;
  12.     }
  13.     return n;
  14. }
(the n variable is there because i need it for debugging purposes)

Honestly, I only used the call method because I saw another script use it and I thought it looked cool. :P
I assumed it worked identical to normal calling syntax which appears not to be the case, atleast not on my firefox. Can anyone confirm if there is a difference between these two lines of code?

Expand|Select|Wrap|Line Numbers
  1. someFunction("parameter")
  2. someFunction.call("parameter")
<Edit>And yes, it does alert text node objects for whitespace nodes with the new code
Nov 21 '07 #10
gits
5,390 Expert Mod 4TB
hi ...

the following is a regular function call:

Expand|Select|Wrap|Line Numbers
  1. func(param);
  2.  
the call() method may receive more than one parameter ... where the first parameter is used as the scope that the function should be called in ... so when we use:

Expand|Select|Wrap|Line Numbers
  1. func.call(param, param1);
  2.  
then param is used for the scope and param1 as function-parameter ... but as far as i can see the code i fixed for you works as intended ... the fn alerts the correct nodeType for textnodes ... because the this is the node-context itself in the case of passing the node to the function.call(node) ... so to check that could you please post your html that produces the error? and/or the fn-code?

kind regards
Nov 21 '07 #11
While you did answer my question as to how the call function works, and i tested it to assure i understood, this definition explains why it did not work.

when you say this:
where the first parameter is used as the scope that the function should be called in
That means that when i was calling the function previously, i was sending the node as the context, and not as a parameter for the function body. For my code to work this way, i need to refer to the this object rather than the node parameter i was trying to access.
Nov 21 '07 #12
gits
5,390 Expert Mod 4TB
While you did answer my question as to how the call function works, and i tested it to assure i understood, this definition explains why it did not work.

when you say this:


That means that when i was calling the function previously, i was sending the node as the context, and not as a parameter for the function body. For my code to work this way, i need to refer to the this object rather than the node parameter i was trying to access.
exactly ;)

kind regards
Nov 21 '07 #13
this will teach me to use random functions without knowing what they do :P

this has been very instructive, thx very much :)
Nov 21 '07 #14
gits
5,390 Expert Mod 4TB
glad to hear that :) ... post back to the forum anytime you would have more questions ...

kind regards
Nov 22 '07 #15

Sign in to post your reply or Sign up for a free account.

Similar topics

2
by: Andy Fish | last post by:
Say I am in an XSLT template with the context node set to a node from an alternative document (i.e. read by the document() function). Is there any way to select nodes from the original document...
12
by: Kepler | last post by:
How do you get the height of the client browser in IE? Both document.body.clientHeight and document.body.offsetHeight return the height of the document. If the page is long and there's a vertical...
136
by: Matt Kruse | last post by:
http://www.JavascriptToolbox.com/bestpractices/ I started writing this up as a guide for some people who were looking for general tips on how to do things the 'right way' with Javascript. Their...
4
by: Jim | last post by:
Hi I'm looking to take an existing XML document, query for certain nodes, and 'recreate' the document with just the relevant nodes. I'm currently using XPath - I have established the pattern that...
2
by: Björn Langhof | last post by:
Hello. I want to evaluate a XPath-Expression only on a subtree of the whole xml-document. 1. I select a node of the XML-document 2. Then a want to select specific nodes below the node chosen...
1
by: shellon | last post by:
Hi all: when I use XPather(a firefox extension) to evaluate the expression: "/html/body/table/tbody/tr/td/table/tbody/tr/td/div/ul/li" it tells me there are 7 matching Nodes. but when I use...
2
by: Andy | last post by:
Hi, I have an XML document that uses namespaces (it is from a Word 2007 file). I want to retrieve all the "t" elements that belong to the "w" namespace (<w:t>) using XPath from VB.NET 2003 (.NET...
7
by: martinfrompi | last post by:
I have a container of XmlNodes. Some of them have been removed from the document, some haven't. Is there an easy way to tell which are which? I suppose bool IsPartOfTree(XmlNode node) {...
2
by: nicky123 | last post by:
Hi everyone, This is a brief description that I have provided for parsing & displaying an XML document using DOM API. Please feel free to post your own comments & views regarding...
0
by: ryjfgjl | last post by:
In our work, we often receive Excel tables with data in the same format. If we want to analyze these data, it can be difficult to analyze them because the data is spread across multiple Excel files...
0
by: emmanuelkatto | last post by:
Hi All, I am Emmanuel katto from Uganda. I want to ask what challenges you've faced while migrating a website to cloud. Please let me know. Thanks! Emmanuel
0
BarryA
by: BarryA | last post by:
What are the essential steps and strategies outlined in the Data Structures and Algorithms (DSA) roadmap for aspiring data scientists? How can individuals effectively utilize this roadmap to progress...
1
by: nemocccc | last post by:
hello, everyone, I want to develop a software for my android phone for daily needs, any suggestions?
0
by: Hystou | last post by:
There are some requirements for setting up RAID: 1. The motherboard and BIOS support RAID configuration. 2. The motherboard has 2 or more available SATA protocol SSD/HDD slots (including MSATA, M.2...
0
by: Hystou | last post by:
Most computers default to English, but sometimes we require a different language, especially when relocating. Forgot to request a specific language before your computer shipped? No problem! You can...
0
Oralloy
by: Oralloy | last post by:
Hello folks, I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>". The problem is that using the GNU compilers,...
0
by: Hystou | last post by:
Overview: Windows 11 and 10 have less user interface control over operating system update behaviour than previous versions of Windows. In Windows 11 and 10, there is no way to turn off the Windows...
0
tracyyun
by: tracyyun | last post by:
Dear forum friends, With the development of smart home technology, a variety of wireless communication protocols have appeared on the market, such as Zigbee, Z-Wave, Wi-Fi, Bluetooth, etc. Each...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.