World: r3wp
[Core] Discuss core issues
older newer | first last |
Steeve 15-Dec-2010 [811] | I try to swap [[a b 1 d z 3] [X 3 Y ]] minus the sub blocks |
Ladislav 15-Dec-2010 [812] | OK, thanks |
Andreas 15-Dec-2010 [813] | Not optimal, but a start: bubble-to-front: funct [series index] [for i index 2 -1 [swap b: at series i back b] series] swap-sub: funct [series position] [loop (n: length? series) - position + 1 [bubble-to-front series n] series] |
Sunanda 16-Dec-2010 [814] | I've written some very clunky code that I'd be ashamed to post as a solution. But I can offer you an algorithm that acheives the effect in N-1 swaps at most where N is the sum of the lengths of the two sequences. It's the more-or-less same algorithm used by Andreas. Here's how it works. Given these two sequences: a b c 1 2 3 4 5 6 7 Step1: cyclically rotate the longer sequence M times, where M is the difference in length of the sequences. So in this case, we rotate 3 (7 - 4) times: a b c 4 5 6 7 1 2 3 Step2: swap the elements of the shorter sequence with the tail of the longer one: 1 2 3 4 5 6 7 a b c And it's done. The cycling in place is the tricky part. It can be done, but my code is just too ugly to share :( Andreas's bubble-to-front is an elegant approach to doing the cycling, but is not optimed to reduce the number of steps. It's a managable sub-problem that is a challenge to solve, so I am sure someone can do better than me :) |
Ladislav 16-Dec-2010 [815x3] | ; helper function: swap-first: func [ {swap the first elements of A and B} a [series!] b [series!] /local t ][ set/any 't first a change/only a first b change/only b get/any 't ] |
; implementation: swap-sub: func [ {swap the subseries using the SWAP-FIRST function} a [series!] b [integer!] /local la lb pa pb ][ pa: a la: b - 1 pb: skip a la lb: (length? a) - la while [all [la > 0 lb > 0]][ either la <= lb [ loop la [ swap-first pa pb pa: next pa pb: next pb ] pb: skip pa la lb: lb - la ][ pa: skip pa la - lb loop lb [ swap-first pa pb pa: next pa pb: next pb ] pa: skip pa negate la la: la - lb pb: skip pa la ] ] a ] | |
but, I do not have a proof at hand, that it is optimal | |
Sunanda 16-Dec-2010 [818] | I had a similar volume of code, but not nearly as neat, Ladislav. The problem somehow feels that it ought to have a one-liner solution; but the constaints on what can be used in the code make that hard to find :) |
Rebolek 16-Dec-2010 [819] | looks more like rebcode :) |
Sunanda 16-Dec-2010 [820] | When you take away everything that makes REBOL REBOL, there's not much left :) |
Anton 16-Dec-2010 [821] | Steeve also forgot to mention that you're not allowed to use syntax. |
Sunanda 16-Dec-2010 [822] | :/) |
Ladislav 16-Dec-2010 [823x4] | this may look more readable: ; implementation: swap-n: func [ {swap n elements} a [series!] b [series!] n [integer!] ][ loop n [swap-first a b a: next a b: next b] ] swap-sub: func [ {swap the subseries using the SWAP-FIRST function} a [series!] b [integer!] /local la lb pa pb ][ pa: a la: b - 1 pb: skip a la lb: (length? a) - la while [all [la > 0 lb > 0]][ either la <= lb [ swap-n pa pb la pb: skip pa la lb: lb - la ][ pa: skip pa la - lb swap-n pa pb lb pa: skip pa negate la la: la - lb pb: skip pa la ] ] a ] |
aha, it is wrong, this way | |
swap-sub: func [ {swap the subseries using the SWAP-FIRST function} a [series!] b [integer!] /local la lb pa pb ][ pa: a la: b - 1 pb: skip a la lb: (length? a) - la while [all [la > 0 lb > 0]][ either la <= lb [ swap-n pa pb la pa: pb pb: skip pa la lb: lb - la ][ swap-n skip pa la - lb pb lb la: la - lb pb: skip pa la ] ] a ] swap-first: func [ {swap the first elements of A and B} a [series!] b [series!] /local t ][ k: k + 1 set/any 't first a change/only a first b change/only b get/any 't ] k: 0 swap-sub [1 2 3 4 5 6 7 8 9] 7 k ; == 6 | |
So, Sunanda, how many swaps you are getting? | |
Sunanda 16-Dec-2010 [827] | If the two series lengths are L1 and L2, I get L1+L2-1 swaps -- at most. But there are exceptions, eg: [a b c d 1 2] Needs only 4 swaps....An any [{L1 // L2) = 0 (L2 // L1) = 0] test triggers a shortcut. However .....I also have some edge-case bugs in my code -- so you win!! |
Claude 16-Dec-2010 [828x2] | /9c=8O%%%%%%%%%%%%%%%%%%%%0P/*****5%('rrrrrrrrbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb |
OUPS my cat on my keyboard ;-) | |
Pekr 16-Dec-2010 [830] | :-) |
Henrik 16-Dec-2010 [831] | Claude, use the little pencil above the typing area for multi-line text. That might reduce accidental sending :-) |
Steeve 16-Dec-2010 [832x2] | Thanks for your hard work. I didn't read your proposals yet, though. I think I found the optimal way. As you noticed, it involves modulo maths. swap-sub: func [s pos /local len e sav][ -- pos sav: s forever [ e: skip s pos len: length? s loop len - pos [swap ++ s ++ e] if zero? len // pos [break] pos: pos - (len // pos) ] sav ] |
Now I will rewrite it, with different input parameters, so that it can swap sup-parts of larger series. | |
Sunanda 16-Dec-2010 [834] | That looks good steeve -- short, neat code, looks optimal on the swap numbers. And a completely different algorithm to mine. |
Steeve 16-Dec-2010 [835] | The swap numbers may be optimal, but it appears to me than the code may be faster. if one swap the ++ operator with -- in some cases, then one may reduce the number of forever loops needed. But the swap number ober the serie will remain the same. |
Steeve 17-Dec-2010 [836] | How to waste his time ? Get ladislav's mergesort working in-place. --> done |
Sunanda 17-Dec-2010 [837] | Is it faster that way? |
Steeve 17-Dec-2010 [838] | Slower, the algorithm more complex, lot of swap. If it was compiled, maybe... |
Ladislav 18-Dec-2010 [839] | I wonder, whether the majority of users prefer POKE to stay as-is, or would welcome it to accept any-type DATA argument? |
Oldes 18-Dec-2010 [840] | I don't use POKE.. what I remeber.. maybe just in some rare cases. |
Anton 18-Dec-2010 [841x2] | Steeve, good fun. I came to a swap-sub using modulo as well, but it only worked for some series lengths, and I had to sleep before figuring out which lengths they were, but they surely included prime numbers. |
(I used only a single loop). I thought maybe I could detect which series lengths could be processed using only a single loop, and other cases could be processed using another algorithm. | |
Anton 25-Dec-2010 [843] | Steeve, did you finish the swap-sub yet? Curious. |
Steeve 25-Dec-2010 [844] | It was already, I just changed the inputs for other purposes. |
Anton 25-Dec-2010 [845] | You said above "so that it can swap sub-parts of larger series". Is that what you mean? |
Steeve 25-Dec-2010 [846] | yeah, i just had to pass an extra parameter to set the length of the added sub-parts, instead of calculate it. But the algorithm remains the same. |
Anton 25-Dec-2010 [847x4] | Ok, easy. |
Ladislav, does not POKE DATA parameter already accept argument of any type ? ( I checked only Rebol3 alpha 76 (not most recent) and Rebol2.7.7). | |
Steeve, What might be interesting (and possibly even ... useful) is to generalise to be able to swap (rotate) any number of sub-series, eg. for three sub-series in a series [... AAA ... BBBB ... CC ...] AAA moves to where BBBB is currently, BBBB moves to where CC is currently, and finally CC moves to where AAA is currently. | |
(but not tonight, for me..) | |
Steeve 25-Dec-2010 [851x2] | Should not be that hard with a recursive approach |
(I did not say that I will do it) | |
Ladislav 25-Dec-2010 [853x2] | REBOL 3.0 A110 2-Nov-2010/3:56:20 >> source poke poke: make action! [[ {Returns value after changing its data at the given index. (Modifies)} value [series! port! map! gob! bitset!] index {Index offset, symbol, or other value to use as index} data "New value" ]] >> poke [1] 1 #[unset!] ** Script error: poke does not allow unset! for its data argument |
So, I was curious, what the user preferences are. Current poll state: any-type! DATA : any DATA = 1:0 (counting just myself, no other response obtained) | |
BrianH 25-Dec-2010 [855] | Normally I would like to limit the occasions where an unset! can get through without errors triggered (those errors are the whole point to the unset! type), but in this case the other series manipulation functions accept any-type!, so consistency wins here. +1 any-type!. |
Janko 25-Dec-2010 [856] | anyone did anything with Rebol and JVM (Java) integr/cooper-ation. I need functionality of some big java lib ("server side") in rebol. What would you do or use? |
GrahamC 25-Dec-2010 [857] | add a port to communicate with the java app? |
Anton 26-Dec-2010 [858x2] | Ladislav, oh I see. Yep, +1 any-type! |
Steeve, would need to convert to iterative to stay memory safe. | |
Gregg 27-Dec-2010 [860] | >> blk: copy [1] == [1] >> blk/1: #[unset!] ** Script error: blk/1: needs a value >> poke blk 1 #[unset!] ** Script error: poke does not allow unset! for its data argument >> head insert blk #[unset!] == [unset! 1] What other series funcs are you think of Brian? If any-type! is allowed, should the behavior be like INSERT? |
older newer | first last |