(*
Sample usage of node positions in a PXP (an OCaml XML parser) XML tree
Copyright (C) <2003> Stefano Zacchiroli <zack@cs.unibo.it>
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*)
open Pxp_document ;;
open Pxp_dtd ;;
open Pxp_types ;;
open Pxp_yacc ;;
(* assumption: stuff explained in pxp_creation.ml *)
let dtd = new dtd default_config.warner default_config.encoding ;;
(* slightly different from create_element defined in pxp_creation.ml, the below
function always creates elements with no attributes (see the last argument of
create_element_node: it’s always an empty list [it should be a list of pairs
<attribute_name, attribute_value>]) *)
let create_element name =
create_element_node valcheck:false default_spec dtd name []
;;
let create_data data = create_data_node default_spec dtd data
;;
(* let’s create the root element and 7 other elements, at the moment with no
contents (that is equal to "no child data nodes") and no attributes, all
currently unconnected between each other *)
let root = create_element "root" in
let a = create_element "a" in
let b = create_element "b" in
let c = create_element "c" in
let d = create_element "d" in
let e = create_element "e" in
let f = create_element "f" in
let g = create_element "g" in
(* let’s shape the XML tree, the idea is to create an XML tree like this one:
root
/ | \
a b c
/|\ |
d h e f
|
g
Since we are creating the XML tree from scratch we will use the "set_nodes"
method of PXP nodes that let we redefine from scratch the list of children of a
given node *)
root#set_nodes [a; b; c];
a#set_nodes [d; e]; (* ooops, we forget to create the "h" element, not bad, we
can add it later *)
b#set_nodes []; (* yes, this is useless, shown just for completeness *)
c#set_nodes [f];
d#set_nodes [];
e#set_nodes [];
f#set_nodes [g];
g#set_nodes [];
(* let’s create the missing ’h’ element ... *)
let h = create_element "h" in
(* ... and add it to the children of ’a’ using the "insert_nodes" method to
insert it in 2nd position [ pos:1 because position is 0 based] *)
a#insert_nodes pos:1 [h];
(* just to be convince ourselves that all worked well, we ask a’s children their
position wrt its parent: ’d’ should be child number 0, ’h’ child number 1 and
’e’ child number 2 *)
Printf.printf "’d’ element is children number %d of ’a’\n" d#node_position;
Printf.printf "’h’ element is children number %d of ’a’\n" h#node_position;
Printf.printf "’e’ element is children number %d of ’a’\n" e#node_position;
(* finally let’s play with node path to reach element ’g’, it should be [2;0;0]
because you have to follow child number 2 of the root node, than child number 0
of the reached node and finally child number 0 of the reached node is ’g’ *)
Printf.printf
"Path to reach ’g’ from ’root’ is: %s\n"
(String.concat ", "
(List.map string_of_int g#node_path));
(* dump to stdout just to see the result *)
root#write (`Out_channel stdout) `Enc_utf8