World: r3wp
[All] except covered in other channels
older newer | first last |
Pekr 4-Sep-2006 [2277x2] | but that is just my non-native english perspective, which came to my mind few times, without actually thinking more deeply about consequences ... |
as to found? select ... dunno if it is valid thinking - you are not searching the series, altough reading the expression "in english" might suggest it - you are performing found? on the result of select function call .... | |
Ladislav 4-Sep-2006 [2279] | right, Pekr, I mentioned the SELECT issue because it is "at the heart" of the SWITCH problem |
Oldes 4-Sep-2006 [2280x2] | Using found? select .. can be problem anyway as the selected value can be 'none (you found 'none) :-)) I'm not using found? much often i prefere none? and not none? (found? is a shortcut anyway) |
(sorry I can see pekr founded this issue as well:-) | |
Ladislav 4-Sep-2006 [2282] | how about the SWITCH question? |
sqlab 4-Sep-2006 [2283] | >> to logic! select [a b 0] 'b == false |
Ladislav 4-Sep-2006 [2284] | aha, that doesn't look good either |
sqlab 4-Sep-2006 [2285] | This is also problematic |
Gabriele 4-Sep-2006 [2286x6] | i got that bounce email after my last post today too. |
maybe someone subscribed to the list is bouncing? although the error message refers to a mail loop. | |
select reduce [1 none] 1 is the same problem as pick reduce [none] 1 and so on... the problem with switch can be considered a bug, however switch expects a block after the value so this is debatable. | |
i think, that since we have other ways to check for existence (find for select, or length? for pick), the behavior is still acceptable because useful in many cases. | |
of course, Ladislav's /default approach would probably be better. | |
(but can never solve the switch problem completely, because any value used as default could appear in the block - you have to use find) | |
Ladislav 4-Sep-2006 [2292x3] | right, Gabriele, but SWITCH can be implemented using FIND, which would solve this issue |
switch expects a block after the value so this is debatable. - how about switch/default 1 [1 #[none]] [2] then? | |
sorry, forget about it, I just want to say, that SWITCH doesn't check the value is followed by a block | |
Gabriele 5-Sep-2006 [2295x3] | yes, i agree it's a problem, it's just not a problem in practice :) |
i'd actually implement switch using parse. i find it very useful to be able to specify multiple values for the same block. | |
i.e. switch val [2 4 6 ['even] 1 3 5 ['odd]] | |
Ladislav 5-Sep-2006 [2298x4] | that is what Cyphre wants too |
a possible implementation: | |
switch1: func [ "Selects a choice and evaluates what follows it." [throw] value "Value to search for." cases [block!] "Block of cases to search." /default case [block!] "Default case if no others are found." /local blk ][ value: find cases value if value [value: find next value block!] either value [do first value] [if default [do case]] ] | |
it is slower than SWITCH due to "double search", though | |
Anton 5-Sep-2006 [2302x2] | I like that behaviour. I planned to write something similar for a long time... :) |
Mmm.. parsing numbers... | |
Volker 5-Sep-2006 [2304] | How much effort is a switch in c? |
Anton 5-Sep-2006 [2305x2] | switch2: func [ "Selects a choice and evaluates the first block that follows it." [throw] value "Value to search for." cases [block!] "Block of cases to search." /default case [block!] "Default case if no others are found." /local rule ][ rule: [ 1 1 () ; <-- value to block! set value block! (return do value) to end | skip to () ; <-- type? value ] rule/3: value change back tail rule type? value any [ parse cases [some rule] do case ] ] ;test repeat n 10 [ print [ n switch2/default n [2 4 6 ['even] 1 3 5 ['odd]] [mold "--default--"] ] ] switch2 1 [] switch2/default 1 [] ["--default--"] |
Actually, don't need to wrap the final two lines in the ANY block. | |
Ladislav 5-Sep-2006 [2307] | >> switch 1 [1 [2]] == 2 >> switch1 1 [1 [2]] == 2 >> switch2 1 [1 [2]] ** Throw Error: Return or exit not in function ** Where: switch2 ** Near: return do value |
Anton 5-Sep-2006 [2308x6] | fixing it right now... |
I think it's fixed, but I'm also working on a version which evaluates the action block for every value and following block found. | |
That could be useful, allowing intersections of behaviours. | |
(and should not interfere with the usual usage we are used to.) | |
How about this: | |
switch2: func [ "Selects a choice and evaluates the first block that follows it." [throw] value "Value to search for." cases [block!] "Block of cases to search." /default case [block!] "Default case if no others are found." /local rule ][ rule: [ 1 1 () ; <-- value to block! set case block! ; <- re-use the 'case variable to end | skip to () ; <-- type? value ] rule/3: value change back tail rule type? value parse cases [some rule] do case ] {switch2: func [ "Selects a choice and evaluates the first block that follows it. This occurs for every matching value and following block found." [throw] value "Value to search for." cases [block!] "Block of cases to search." /default case [block!] "Default case if no others are found." /local rule ][ rule: [ 1 1 () ; <-- value to block! set case block! (case: do case) ; <- re-use the 'case variable, twice... | [skip to ()] ; <-- type? value | skip ] rule/3: value rule/11/3: type? value any [ all [ parse cases [some rule] case ] do case ] ]} ;test repeat n 10 [ print [ n switch2/default n [2 4 6 ['even] 1 3 5 ['odd]] [mold "--default--"] ] ] switch2 1 [] switch2/default 1 [] [probe "--default, ok--"] switch2 1 [1 [probe "ok"]] switch2 2 [1 [probe "bad"]] switch2 1 [1 2 [probe "ok"]] switch2 2 [1 2 [probe "ok"]] switch2 3 [1 2 [probe "bad"]] ; multiple action blocks switch2 1 [1 2 [probe "ok"] 1 3 4 [probe "ok#2"]] ; <-- switch2 2 [1 2 [probe "ok"] 1 3 4 [probe "bad"]] switch2 3 [1 2 [probe "bad"] 1 3 4 [probe "ok"]] switch2 4 [1 2 [probe "bad"] 1 3 4 [probe "ok"]] switch2 5 [1 2 [probe "bad"] 1 3 4 [probe "bad"]] switch2/default 5 [1 2 [probe "bad"] 1 3 4 [probe "bad"]] [probe "--default, ok--"] | |
Ladislav 5-Sep-2006 [2314] | looks slightly slower than the FIND-based version according to my measurements |
Gabriele 5-Sep-2006 [2315x3] | parse block [to value to block! ...etc...] |
if TO doesn't behave (i remember the "feature" with integers...) then maybe: | |
parse find block value [to block! ..etc..] | |
Anton 6-Sep-2006 [2318x2] | Ladislav. Hmm.. that's a bit disappointing, although understandable. It's a complex parse rule with some time spent in setup. |
I'm enamoured with the multiple action block version, so I'll see if I can make a nice FIND-based version of that. | |
Ladislav 6-Sep-2006 [2320] | I may not understand, doesn't the SWITCH1 above do what you want? |
Anton 6-Sep-2006 [2321x2] | Uncomment my second switch2 and have a look at the first test under "multiple action blocks". |
For that test, both "ok" and "ok#2" should be printed. | |
Ladislav 6-Sep-2006 [2323x2] | aha, this is what you are after |
it would be interesting to know how many users would want this feature - I am afraid it can help to hide a programming error | |
Anton 6-Sep-2006 [2325x2] | That's true. I will definitely be keeping it in my library though. |
Can you remind us of the effect of [throw] on return etc.. ? | |
older newer | first last |