World: r3wp
[Core] Discuss core issues
older newer | first last |
Louis 31-Aug-2007 [8655x2] | Whoops! Watch out for wordwrap. |
Sorry. I see it now. My mistake. | |
DanielSz 31-Aug-2007 [8657] | Exactly, Graham, argument passing in a block is a decent solution. I saw here and there rebol code implementing this for similar purposes. I'll repost a an updated 'retry version when I get around it. |
Louis 31-Aug-2007 [8658] | Attention whoever is in charge of documentation. Section 11.12 of the Core Users Manual give an example that will not work. A clear buffer statement is needed after the write-io line, and the ports need to be closed after sending each file. |
DanielSz 31-Aug-2007 [8659x4] | Gregg, do you mean Finite State Machine. Care to expand? |
Ok, here is an updated version of 'retry. What is it? It is a higher -level function that takes as input a user function and repeats it the number of times specified. The current version handles user functions that take arguments. | |
Usage: retry :user_function 5 For a user function that doesn't take arguments retry/args :user_function 5 [args] For a user function that take arguments retry: func [user_function [function!] retries [integer!] /local .retry [function!] tries [integer!] value [any-type!] args_length [integer!] /args block [block!]] [ tries: 0 args_length: length? first :user_function if ((args_length > 0) and (not args)) [print ["User function require" args_length "arguments. Provide them in a block and use the /args refinement."] return] if not args [args_length: 0 block: []] .retry: func [.user_function [function!]] [ either not error? try [value: do compose [.user_function (copy/part block args_length)]] [ if not unset? value [return value] ] [ print "Retrying..." tries: tries + 1 if tries > retries [print rejoin ["Tried function " tries " times. Exiting"] return] .retry :.user_function ] ] .retry :user_function ] Everybody is invited to improve on this. | |
I wrote 'retry to use in scripts heavy in network calls where failure is, by nature of the internet, common, so instead of aborting when such a failure occurs, I can use 'retry to repeat individual functions any number of times I wish, improving the success of the script. | |
Gabriele 1-Sep-2007 [8663x2] | >> retry: func [code times] [ [ loop times [ [ attempt [ [ break/return do code [ ] [ ] [ ] |
>> retry [1 / probe -1 + random 2] 5 0 1 == 1 | |
DanielSz 1-Sep-2007 [8665x5] | Very elegant, and concise, Gabriele. Maybe you can propise have an expanded version to handle arguments the code should be invoked with |
Sorry, I pressed Enter by mistake, here I go again: Very elegant, and concise, Gabriele. Maybe you can propose an expanded version that can handle arguments that the code should be invoked with. | |
That's what 'retry currently does. | |
If you provide that capabilty, I take your version in no time. Mine is too obscure. | |
Another requirement is tthat if the code returns a value, retry should return that exact same value as well. I believe your version currently doesn't. | |
Ingo 1-Sep-2007 [8670x2] | After reading about /no-set to reduce, is this an error? / inconsistency? >> reduce ['s: 3 * 3] == [s 9] |
shouldn't it be == [s: 9] ? | |
Gabriele 1-Sep-2007 [8672x3] | Daniel, since my version takes a block, you can pass as many args as needed. |
example: retry [user-function arg1 arg2 arg3 ...] 5 | |
of course, it could be enhanced by reporting the error instead of returning none if it fails more than the given times, and so on. | |
DanielSz 1-Sep-2007 [8675x10] | I was going to apologize to you, Gabriele, a few minutes ago I had the sudden realization that your version can indeed handle user-function with arguments, as your latest post explains. |
Your version really makes rebol shine. Its expressiveness is beyond par. Bravo. | |
Gabriele, just one thing, imagine the following user function: f1: func [] [return "f1 body"] | |
Now: retry f1 4 yields none. | |
It should return "f1 body", no? | |
Antoher issue that might be a rebol bug is the use of attempt. Normally attempt should return a none value when an error occurs, but consider this. | |
f2: func [] [ do [1 + "x"]] | |
>> retry f2 4 ** Script Error: Cannot use add on string! value ** Where: f2 ** Near: 1 + "x" | |
That's not what we want. | |
Again apologies, again my stupidity, all the issues I raised in the latest posts are non issues, I made a mistake referencing my functions, it should be retry :f1 4, retry :f2 4 (note the colon before the function name). and then it behaves as expected. Thanks, Gabriele, for this humbling lesson in rebol. | |
[unknown: 5] 1-Sep-2007 [8685] | shouldn't poke work on port data if pick does? Seems strange behavior for it not to |
Gabriele 2-Sep-2007 [8686x2] | i'd actually suggest retry [f1] 4 or retry [f2] 4 with my code. :f also works but if f takes arguments it would break. so it's cleaner to just always use a block. |
actually, there is one problem with return, which is if you want to do retry [... return 'something ...] and have it return from the calling function, not retry (like if cond [return 'something]). to allow that, you need to add the [throw] func attribute, ie. retry: func [[throw] code times] ... | |
DanielSz 2-Sep-2007 [8688x2] | Thanks for the advice, Gabriele, I'll play around with it for a while... |
Gabriele, I'm trying to understand in what kind of situation a throw is required. f1: func [] [if true [return "something"]] works without a throw, for example. Can you provide a concrete example of code that requires the throw attribute to 'retry? Thanks! | |
Gabriele 3-Sep-2007 [8690x3] | i'm not sure it is needed or not for retry. it depends on how you use it. |
f: func [] [ retry [ ; do something... if cond [return something-else] ; ... ] some-val ] | |
if you want the return inside retry to return from F and not RETRY, then you need [throw]. | |
DanielSz 3-Sep-2007 [8693] | Thanks, Gabriele, I haven't thought about that. |
Joe 4-Sep-2007 [8694x3] | is the sort block dialect broken ? |
b-test: ["xxx" "V" 4 "xxx" "M" 3 "yyy" "Laaaa" 2 "yyy" "Lbbbb" 2 "yyy" "Kaaaa " 2 "yyy" "Haaaa" 2 "yyy" "Aaaaa" 2] print ["init " mold b-test] sort/skip/compare b-test 3 [reverse 3 2] print ["reverse 3 2 " mold b-test] sort/skip/compare b-test 3 [reverse 3 reverse 2] print ["reverse 3 reverse 2" mold b-test] | |
It seems to use the first reverse 3 but ignore the second comparator. Any ideas ? | |
btiffin 4-Sep-2007 [8697x2] | Joe; I think you need to pass sort/compare a function! not a block! The function template is [a b] and returns true or false or whether to swap. Something like sort/compare data func [a b] [a > b] (Note: the names a and b could be any words but the function is called with two arguments). |
Never mind my blabbering. Learned something new today. :) | |
Graham 5-Sep-2007 [8699] | Can someone remind me how bind a bunch of words to a different context? I want to use the named colors in a special context. |
Chris 6-Sep-2007 [8700] | colors: context [red: 255.0.0 green: 0.255.0 blue: 0.0.255] reduce bind [red green blue] in colors 'self |
Graham 6-Sep-2007 [8701] | I'll give it a go :) |
[unknown: 5] 6-Sep-2007 [8702] | anyone know if REBOL runs on PocketPC? |
Graham 6-Sep-2007 [8703x2] | core used to ... |
wince 1.1 ? | |
older newer | first last |