r3wp [groups: 83 posts: 189283]
  • Home
  • Script library
  • AltME Archive
  • Mailing list
  • Articles Index
  • Site search
 

World: r3wp

[XML] xml related conversations

BrianH
24-Jun-2009
[708]
OOP in a prototype-based language with function values instead of 
methods is different. Classes are emulated if need be, but don't 
always need to be. In REBOL even delegation is explicit, unlike most 
other prototype-based object languages.


For the best maintenance use factory functions that create objects 
based on standard specs. Beyond that, different models are better 
for different tasks. Sometimes you assign function values to fields, 
sometimes you use class objects, sometimes class names that are looked 
up at runtime.
Maxim
24-Jun-2009
[709]
I usually creat myself a new function which calls make and the  object 
init (wether class or prototype based)  if that init needs to create 
new inner objects, then its responsible for doing so.


in your case the make-xml-object  could accept an xml string and 
then call make-xml-object recursively for each element it finds.
Graham
24-Jun-2009
[710]
I guess I can set the init functions to none after they've done their 
jobs ?
Maxim
24-Jun-2009
[711]
not much would really be gained, but it migh trigger some GC cleanup.
Graham
24-Jun-2009
[712x2]
i wouldn't have 100s of init functions anymore .. :)
Using your method of creating a special context is going to screw 
up my obj2xml function :(
Sunanda
24-Jun-2009
[714]
One way to do init is as open code in the object....That only "inits" 
the original object, not anything MAKEd from it. But it may be useful 
in some cirumstances, and it does not become part of the object:
    o: make object! compose [print "init" (a: 99) a: 1 b: 2]
Graham
24-Jun-2009
[715]
huh?
BrianH
24-Jun-2009
[716]
Code in the spec block doesn't get attached to the object.
Maxim
24-Jun-2009
[717x2]
thats another ways of doing it... instead of storing reference objects 
you store reference spec blocks.
that is how its done in GLayout to assign the same setup to many 
styles.
BrianH
24-Jun-2009
[719]
The spec block is like an init function that goes away after it runs, 
without needing to assign none to any fields.
Maxim
24-Jun-2009
[720]
so graham... instead of doing: 


; note this is an object, context is a shortcut for make object! 
,  like func is a shortcut for make function!
addressobj: context [
	number: 666
	street: "styx lane"
	city: "pandemonium"
]
pharmacy: context [
	address: make addressobj [ ]
]

you do:

; note this is a block
addressobj: [
	number: 666
	street: "styx lane"
	city: "pandemonium"
]

pharmacy: context [
	address: context addressobj
]
Graham
24-Jun-2009
[721]
I'm having to create nested objects 7 levels deep ...
Maxim
24-Jun-2009
[722x2]
in the later, you can add code in the addressobj which will be executed 
everytime you create an object using it.

for example: 
addressobj: [
	number: 666
	street: "styx lane"
	city: "pandemonium"
	address: rejoin [number " " street " " city]
]
does the xml structure change a lot (lists of data, alternative or 
optional elements, etc) or is it really static?
Graham
24-Jun-2009
[724]
static largely
Maxim
24-Jun-2009
[725x4]
cause with rebol its easy to hack stuff up using out of the box tricks.....
something like...
>> probe load replace {#[object! [a: #[object! [b: #[object! [c: 
"%VALUE%"]]]]]]} "%VALUE%" "tadam!"
make object! [
    a: make object! [
        b: make object! [
            c: "tadam!"
        ]
    ]
]
;-)
Graham
24-Jun-2009
[729x2]
A hack.
The XSD I'm looking at has about 30-40 complex data types
Maxim
24-Jun-2009
[731]
my client has a few thousand data types to cope with ;-) rebxml allows 
you to load that up pretty quickly...but not using the xsd obviously.


its parser builds up a string and then loads it.   I found it to 
be quite fast actually.  its MUCH faster than firefox, for example.
Graham
24-Jun-2009
[732x2]
I'm creating the XML from scratch .. and not reading it in.
Maybe I need to use the factory way ..
Maxim
24-Jun-2009
[734x3]
you only need to output xml?  then that is very easy.
MUCH easier than loading it.
what is the source of data?
Graham
24-Jun-2009
[737x3]
well, output is first, reading is the next task :)
it's all in a DB.
this is part of the xsd .. found an example http://stackoverflow.com/questions/790118/jaxb-types-problem
Maxim
24-Jun-2009
[740x2]
what I can suggest is that you build your objects like so:

xml-attribute: context [
	name: "someattr"
	value: "somevalue"
]

xml-tag: context [
	name: "FileID"
	content: []  ; a block of inner xml-tag objects
	attributes: [] ; a block of xml-attribute names
]



then all you do is nest objects in objects, filling them up item 
by item recursively using DB data.
the downside is that access either needs a wrapper func, or is done 
via indexes...


actually attributes could be an object, since their names are mutually 
exclusive within an element.
Graham
24-Jun-2009
[742]
Let me understand this .. if I have an object that needs other objects 
more than 1 deep .. I can't use that to clone other objects without 
creating references instead of copies.
Maxim
24-Jun-2009
[743]
you can just do a mold/all load, that will in effect copy the whole 
tree along with all the series too.
Graham
24-Jun-2009
[744]
I was just thinking that.
Maxim
24-Jun-2009
[745x2]
ex:

load mold/all make object! [
    a: make object! [
        b: make object! [
            c: "tadam!"
        ]
    ]
]


will effectively create a complete duplicate of the whole object 
tree.
but remember to use mold/ALL  cause otherwise you end up with gibberish...
Graham
24-Jun-2009
[747x2]
So, I can continue to make the objects as I have been doing.  But 
just before I use it ... I load mold/all on it to ensure I have unique 
objects
ie. I load a serialized form of the object
Maxim
24-Jun-2009
[749]
yes.
Graham
24-Jun-2009
[750x2]
ahh ... well problem solved :)
seems not :(

>> pharmacy: make object! [
[     name: none
[     init: func [ n ][
[          self/name: n
[         ]
[    ]
>> a: load mold/all make pharmacy []
>> probe a
make object! [
    name: none
    init: func [n][
        self/name: n
    ]
]
>> a/init "testing"
** Script Error: self has no value
** Where: init
** Near: self/name: n
Maxim
24-Jun-2009
[752x2]
if you have a function inside, I think you have to do it instead 
of load it.
functions cannot be serialized... so they have to be bound somehow.
Sunanda
24-Jun-2009
[754]
Why not remove the self ? [not a metaphysical question in this context]
    ph: make object! [
        name: none
        init: func [n][
            name: n
        ]
    ]
Maxim
24-Jun-2009
[755]
seems functions can be serialized, but I don't understand why the 
self isn't being bound to the object..that is strange.
Graham
24-Jun-2009
[756]
because it won't work?
Maxim
24-Jun-2009
[757]
ok, to use do, you must forget the /all.


so the above, minus the /all should work with self... (it does in 
my tests)