World: r3wp
[Core] Discuss core issues
older newer | first last |
Ladislav 22-May-2006 [4613x2] | (or unbound, in my version of the function) |
It looks, that we don't know what exactly you want to accomplish, and it is a bit hard to guess. Could you be more specific? | |
Joe 22-May-2006 [4615x5] | I am using linux and the clipboard doesn't worked so I typed the code |
unbind: func [ "unbind words" [catch] words [word! block!] /local word result object ][ if word? words [words: reduce [words]] result: copy [] unless parse words [ any [set word word! (insert tail result to set-word! word)] ][ throw make error! "unexpected data" ] exclude: result [self:] insert tail result none object: make object! result either find result first [self:] [first object] [ exclude first object [self] ] ] blk: [a b] a: 1 b: 2 f: func [/local res][ res: bind/copy unbind blk 'res a: 1 b: 1 probe reduce res ] f blk | |
** Script Error: self has no value ** Where: f ** Near: self >> | |
I get the same error when commenting a: 1 b: 1 line inside f | |
Ladislav, thank your help. I wanted to ask you about this via the mailing list and I did send the message earlier this morning but the mailing list is down. Please bear with me and I will provide the details. I think the solution you provided is exactly what I was looking for but I might be missing some detail. I am studying your code right now and will be more specific in a few minutes | |
Gregg 22-May-2006 [4620] | Could you write the steps of the problem domain in pseudo-code for us? i.e. forget about the implementation for the moment. |
Joe 22-May-2006 [4621] | i am preparing the pseudo-code. just a few minutes |
Ladislav 22-May-2006 [4622x2] | your code contains the following bug: exclude: result [self:] |
the original line is exclude result [self:] | |
Joe 22-May-2006 [4624x6] | thanks. I will post real code because I think it explains the problem better |
template: to block! "<html><head><title> title </title></head><body>tag1 tag2 tag3</body></html>" blk: remove-each val load copy template [tag? val] ?? blk ; == [title tag1 tag2 tag3] tag3: "this is a fake value, should not appear" eval-template: func [ /local res ][ res: copy "" title: "hey" tag1: "this is tag1^/" tag2: "i am tag 2^/" ;tag3: "might not be set^/" bind/copy template 'res repend res template res ] | |
sorry pls look at the next example | |
template: to block! "<html><head><title> title </title></head><body>tag1 tag2 tag3</body></html>" blk: remove-each val load copy template [tag? val] ?? blk ; == [title tag1 tag2 tag3] tag3: "this is a fake value, should not appear" eval-template: func [ /local res ][ res: copy "" title: "hey" tag1: "this is tag1^/" tag2: "i am tag 2^/" ;tag3: "might not be set^/" bind/copy unbind blk 'res repend res template res ] | |
The unbind function is very close to what I want. In the previous example if the function body does not set the variables a or b it prints [none none]. What I want is that if a variable in blk is not set then it throws an error | |
IPls let me know if this example is not clear. What I want is to catch the case where tag3 is not set and throw an error This is useful where the tags are set in a large function and there are many tags | |
Ladislav 22-May-2006 [4630] | Your EVAL-TEMPLATE function does not have 'TITLE as local variable. Do you want 'TITLE to be local or not? |
Joe 22-May-2006 [4631x2] | I want title to be local without defining it in the spec. Eval template is a function that might be used for many different templates |
IMy understanding is that if you bind a word to the local context then it's a local even if it's not defined in the spec but I probably have multiple misunderstanding (though I just read the Bindology Bible by Ladislav) | |
Ladislav 22-May-2006 [4633x3] | unfortunately that is not true, at least not in this REBOL version |
local contexts are somewhat "static", i.e. they cannot be enlarged | |
(section 15) | |
Gregg 22-May-2006 [4636] | local without defining it in the spec -- I don't think that's a good way to think about modeling it. |
Joe 22-May-2006 [4637] | I see. This is a major limitation. I see the rebol3 has a blog entry that "bind expands contexts" How could I approach this with the current rebol ? |
Anton 22-May-2006 [4638] | No, that's right. Contexts cannot be extended with new words (at this time). I would pass a context to your function with the template and all the words in it. This context will have to be built at the beginning. |
Gregg 22-May-2006 [4639] | It's still not clear to me what the real goal is. i.e. where values come from and how eval-template may be reused without giving it some parameters to guide it. |
Anton 22-May-2006 [4640] | Sorry, I mean you eval-template function can create a context on the fly with the words in it. |
Joe 22-May-2006 [4641] | ok Anton, I will try to implement this with your approach |
Anton 22-May-2006 [4642] | It's not a terribly easy thing to do, but can be done. |
Joe 22-May-2006 [4643] | Gregg, the GOAL is to be able to have a generic eval-template function that can evaluate multiple templates without having to include hundreds of locals in eval template. The values are generated dynamically with a code-block e.g. eval-template template code-block where code-block is [title: func-title "aha" tag1: emit-whatever ... |
Ladislav 22-May-2006 [4644] | hmm, I may not understand your wish, Joe, but don't you want to have it this way? |
Pekr 22-May-2006 [4645] | Today I reread the blog, and I was not comfort with the idea that simple bind should auto-extend context ... maybe just my internal feeling, dunno .... just wanted to state opinion of less experienced reboller :-) |
Ladislav 22-May-2006 [4646] | eval-template: func [ template /local res ] [do something with the template...] |
Anton 22-May-2006 [4647] | Eval-template will accept a template string 1) convert to block 2) extract the words 3) create a context with these words 4) unset all words in the context 5) do your code bound to the context ( do bind your-code the-context ) 6) handle errors 7) return results |
Joe 22-May-2006 [4648] | What I've been using in the past is different versions of eval-template for each template and I found the typical bug to be when missing a local given that the templates are evaluated multiple times |
Anton 22-May-2006 [4649] | After extracting the words you need to convert them all to set-words and put them in a spec block, eg: spec: copy [] foreach word words [append spec to-set-word word] append spec none ; now you can create the context using the spec the-context: context spec ; now unset each word in the context, etc.. |
Joe 22-May-2006 [4650] | Yes anton, I will code it this way. I am worried that unbinding the words every time is a performance hit |
Anton 22-May-2006 [4651] | Possibly, we can optimize it later. Binding is supposed to be pretty fast in rebol. |
Joe 22-May-2006 [4652] | Ladislav, I will try to communicate better. What do you mean by "don't want to have it this way ?" |
Ladislav 22-May-2006 [4653x2] | eval-template: func [ template /local res ] [do something with the template...] |
I just thought, that you wanted to have a function accepting and processing templates | |
Joe 22-May-2006 [4655] | Yes, my problem is an error handling problem. So far the template blocks are global, and I want to have functions that can build the templates without actually passing the template as a parameter |
Ladislav 22-May-2006 [4656] | it looks, that you actually don't need UNBIND |
Gregg 22-May-2006 [4657x2] | Could I ask again for pseudo-code? I'm having the same problem as Ladislav I think. |
If we could step back and look at the problem, without implementation details, it would help me to understand. | |
Anton 22-May-2006 [4659] | Yes, it's a bit confusing jumping straight into it like this. |
Gregg 22-May-2006 [4660x2] | I'm only asking because I think you're making this a lot harder than it needs to be, but I can't be sure if I don't understand the problem. |
I've found that I can make things hard for myself, if I fight REBOL, or easy, if I don't. :-) | |
Anton 22-May-2006 [4662] | Yes, I can't say I find myself needing to do such an operation very often. Been a while since I generated html though. |
older newer | first last |