REBOL

REBOL3 - Core-old (Discuss core issues [web-public])

Return to Index Page
Most recent messages (300 max) are listed first.

#UserMessageDate
18698SunandaLooks like 35 or so messages are missing from the Core-old group. Those messages are archived here: http://www.rebol.org/aga-display-posts.r?post=r3wp157x18696Sun 22:51
18697CarlTestSun 21:50
18696GreggAnd performance memory issues on large files.Thu 17:48
18695GreggLadislav, yes I saw corruption.Thu 17:47
18694LadislavI do not consider it a bug, but I do want a different behaviour, which I have to simulate somehowThu 14:45
18693GabrieleLadislav: also, I think OPEN without /DIRECT will actually read the file and then write it back, so it's no different from Geomol's solution actually. Gregg's /SEEK/BINARY (actually I think /SEEK implies /BINARY) should work better.Thu 14:44
18692GabrieleLadislav, note that on Unix, the TOUCH command creates the file if it does not exist. so I would not necessarily consider that a bug...Thu 14:41
18691Pekrend of is not correct name. End is end, period :-) 'remove last-of series' would be OK though ...Thu 11:21
18690GrahamCActually I like 'endof ...

so i can do

remove endof series

Thu 10:30
18689GrahamCor 'end or 'hind ..Thu 10:26
18688GrahamCperhaps we need a new function : rear: func [ series ][ back tail series ]Thu 10:24
18687GrahamCwhat's the most efficient ? :)Thu 10:21
18686Oldesor: >> s: "" s/(length? s) == none >> s: "/" s/(length? s) == #"/"Thu 10:18
18685SunandaIs this any better? if "/" = back tail series [print true]Thu 10:12
18684GrahamCall [ not empty? series #'/" = last series ] seems painfulThu 9:59
18683GrahamCWhat's the safest way to check if a string ends in a "/" or not?Thu 9:58
18682Ladislav"Though with the above you can't specify a given timestamp" - that is exactly what is neededThu 6:05
18681Ladislav"Universal except that is corrupts binary files" - did you find any corruption?Thu 6:04
18680GreggSetFileTime is as close as you get.Wed 22:50
18679GreggNo direct API I know of Max, but I'd rather stay portable as well.Wed 22:49
18678GrahamCI think if you want a particular timestamp you would have to use set-modes.Wed 22:30
18677MaximIIRC there are touch-like functions in the winAPi...Wed 22:16
18676GreggThough with the above you can't specify a given timestamp, which is important for general use.Wed 22:08
18675GreggNot standard on Windows.Wed 22:03
18674GrahamCcall "touch.exe"Wed 22:01
18673GreggUniversal except that is corrupts binary files and will be very slow for large files. I don't know if you can be universal, but you can get close:

touch: func [ {touch the given FILE} file [file!] ] [ file: open/seek/binary file append file "" clear tail file close file ]

You just need to remove /binary for R3.

Wed 21:57
18672LadislavSo, this one looks "universal":

touch: func [ {touch the given FILE} file [file!] ] [ file: open file append file "" clear tail file close file ]

Wed 20:29
18671Ladislavso, in 2.7.7 this one does work for me:

touch: func [ {touch the given FILE} file [file!] ] [ file: open file append file "" close file ]

Wed 20:25
18670Ladislavbut, nevermind, I found a work-aroundWed 20:24
18669LadislavThat works only in single-userWed 20:23
18668SunandaNothing if file does not exist: add if exists? file [...]Wed 20:22
18667Ladislavaha, looks like this does not work in 2.7.7 :-(Wed 20:16
18666LadislavThe only problem I am having with it is, that it creates the given FILE, if it does not exist, while I would prefer the function to do nothing in that caseWed 20:15
18665Ladislavthis looks like working, in R2 as well as in R3, can you confirm?

touch: func [ {touch the given FILE} file [file!] ] [ file: open file clear tail file close file ]

Wed 20:07
18664GreggI use get/set-modes for my TOUCH, but it was only for local use.Wed 17:13
18663IzkataOdd... oh wellWed 15:21
18662Ladislavhmm, does not do help here...Wed 15:19
18661Ladislavchecking...Wed 15:17
18660IzkataOn recreating touch: Doesn't writing nothing work? Seems to here...

write/append %Filename {}

Wed 15:17
18659ChristianE*do do = to doWed 13:45
18658Ladislavthat is a problem, I need to touch the file, i.e. change the date, but, nevermind, I can make a work-aroundWed 13:45
18657ChristianESince if it exists, you'll have do do a second OPEN, the file may vanish in the meantime.Wed 13:45
18656ChristianE>> port: open/read %test ** Access Error: Cannot open /c/program files (x86)/rebol/view/test ** Near: port: open/read %test

isn't suited for your purpose, I guess.

Wed 13:44
18655LadislavBut, I need the exact opposite, to open touch a file only if it exists, which looks like not supported...Wed 13:39
18654Pekrin R2, you use open/new for such purpose (to create a file if it does not exist)Wed 13:34
18653Ladislav(in R2)Wed 13:18
18652LadislavHmm, I thought, that OPEN does not create the file when it does not exist?Wed 13:18
18651ChristianEThat was just by luck.Wed 13:13
18650Geomolamazing!Wed 13:12
18649LadislavthanksWed 13:12
18648Ladislavaha, fineWed 13:12
18647ChristianEUsing R3,

>> clear back tail port

works for me.

Wed 13:11
18646GeomolUsing R3, I get: ** Script error: cannot use remove on port! value Probably the same, you see.Wed 13:01
18645GeomolDoing open/binary and it works.Wed 12:59
18644GeomolHere (under windows) a unix format text file is changed to dos format, if I do, what you just suggested. So it become longer.Wed 12:57
18643Ladislav:-(Wed 12:54
18642Ladislav...at least not for me...Wed 12:54
18641GeomolAnd it doesn't work in R3 for some reason?Wed 12:53
18640GeomolyesWed 12:53
18639Ladislavremove back tail port is what I meantWed 12:52
18638GeomolNeat! :)Wed 12:52
18637Ladislavport: open %file remove back tail file close portWed 12:52
18636GeomolCould you show me?Wed 12:51
18635GeomolI mean, is it possible in R2?Wed 12:49
18634Ladislavin R2 it is, as it looksWed 12:48
18633GeomolIs that possible?Wed 12:48
18632Ladislav- that is the same for me, I would like to just remove one character, not to copy the whole fileWed 12:47
18631GeomolIs this better with your definition of 'ugly'?

write/binary %file copy/part read/binary %file (get in info? %file 'size) - 1

Wed 12:45
18630Geomolyeah! :-)Wed 12:40
18629Ladislavin R2 it can be simpler, but probably not in R3Wed 12:40
18628Ladislavhmm, uglyWed 12:40
18627Geomol"how to remove the last character from a file in R3?"

I don't know, if it will be done differently in R3, but using R2 I would do something like:

sz: length? p: open/binary %file write/binary %newfile copy/part p sz - 1 close p

Wed 12:39
18626GrahamNow that I think about it .. my NAS box has that problem .. I copy files to it, and the file dates are in the future because the box's time runs fast :(Wed 10:05
18625GrahamyesWed 10:04
18624LadislavI suppose you mean Set-modes?Wed 10:04
18623Grahamie. get-modes can't set directory datesWed 10:03
18622GrahamIn my file replication tool I hit a snag ... when replicating directories I was not able to set the file date :(Wed 10:02
18621Ladislava related problem: how to remove the last character from a file in R3?Wed 10:02
18620Ladislav(I just do not know on which machine the file is)Wed 10:00
18619LadislavrightWed 9:59
18618Grahamno watch??Wed 9:59
18617LadislavActually, that is why I am using the Touch functionWed 9:59
18616Grahamthat implies the resource on pc2 has a touch facilityWed 9:58
18615Ladislav;-)Wed 9:57
18614LadislavThere is: Touch a file and get its timeWed 9:57
18613GrahamThere's no way PC1 can know what time it is on PC2Wed 9:56
18612GrahamHaven't tried ... not for many yearsWed 9:56
18611LadislavDoes the SET-MODES function work for you in R2.7.7?Wed 9:56
18610GrahamI would have thought that logically the file on the other pc is for the time owned by the original pcWed 9:55
18609GrahamYes.Wed 9:55
18608LadislavBTW, did you use the SET-MODES function?Wed 9:55
18607LadislavThat is actually not what I want - suppose that you manipulate a file on a different machine, not using synchronized clockWed 9:52
18606GrahamI think I did that for my directory syncing toolWed 9:37
18605Grahamwhy not just alter the time of the file .. .and if it doesn't exist, then create the file?Wed 9:37
18604Ladislavseems, that it does it differently, but, actually, that method is not suitable for my purposes, I need an "across network" touch, which should be consistent with "storage clock"Wed 9:23
18603Geomoland how it does it.Wed 8:56
18602GeomolMaybe look at a source of "touch" to see, what it does?Wed 8:56
18601GeomolThe UNIX touch create the file, if it doesn't exists. (If you will make sure, that happens.)Wed 8:54
18600LadislavI am wondering what is the simplest method to implement the Touch function in REBOL? Is there anything simpler than to append one character to the file and remove it again?Wed 8:43
18599Maximall I can say is that I felt the same effect when moving from vista to XP. possibly even more.4-Oct 15:27
18598LadislavSo, I am curious, whether somebody would confirm my finding.4-Oct 15:26
18597Maximalmost exactly 20% on the same system.4-Oct 15:24
18596Maxim(vista / w7)4-Oct 15:22
18595Maximwow that's a pretty big differerence!4-Oct 15:22
18594LadislavBenchmark run 4-Oct-2010/17:05:53+2:00. Rebol 2.7.6.3.1 Computer: 100Mega Athlon II 250/4G DDR 3 OS: Windows 7 Professional 64-bit Precision: 0.05 Empty block: 129000000.0Hz Eratosthenes Sieve Prime (size: 8191): 71.4Hz, result: 1899 primes Four-Banger test (+,-,*,/): 188000.0Hz, result: 10.0 Integral (icount: 10000) of sin(x) 0<=x<=pi/2: 51.3Hz, result: 1.00000000000003 Integral (icount: 10000) of exp(x) 0<=x<=1: 75.5Hz, result: 1.71828182845896 Merge Sort (500 elements): 92.5Hz4-Oct 15:15
18593Ladislav(I checked, that the speed difference between 2.7.6 and 2.7.7 is not that big)4-Oct 15:14
18592LadislavHi, did somebody also notice the speed difference between Vista and 7 as below?

Benchmark run 27-Aug-2009/16:16:06+2:00. Rebol 2.7.6.3.1 Computer: 100Mega Athlon II X2 250/4G DDR3 OS: Windows Vista 64 Precision: 0.05 Empty block: 104000000.0Hz Eratosthenes Sieve Prime (size: 8191): 54.0Hz, result: 1899 primes Four-Banger test (+,-,*,/): 150000.0Hz, result: 10.0 Integral (icount: 10000) of sin(x) 0<=x<=pi/2: 42.7Hz, result: 1.00000000000003 Integral (icount: 10000) of exp(x) 0<=x<=1: 60.2Hz, result: 1.71828182845896 Merge Sort (500 elements): 68.4Hz

Benchmark run 4-Oct-2010/17:00:19+2:00. Rebol 2.7.7.3.1 Computer: 100Mega Athlon II X2 250/4G DDR 3 OS: Windows 7 Professional 64-bit Precision: 0.05 Empty block: 131000000.0Hz Eratosthenes Sieve Prime (size: 8191): 69.0Hz, result: 1899 primes Four-Banger test (+,-,*,/): 188000.0Hz, result: 10.0 Integral (icount: 10000) of sin(x) 0<=x<=pi/2: 49.7Hz, result: 1.00000000000003 Integral (icount: 10000) of exp(x) 0<=x<=1: 74.8Hz, result: 1.71828182845896 Merge Sort (500 elements): 90.4Hz

4-Oct 15:14
18591Maxima lot of the APIs have changed in Windows vista/7 (not sure about Clipboard). the kind of changes I would expect... if its not using the latest apis, newer features in the OS could simply be preventing REBOL from accessing this device. just like how these new OS prevent you from writing within the program files folders.

some things which had defaults, maybe now require explicit flags... etc...

4-Oct 14:18
18590PekrIt's possible, that something in REBOL causes it does not work under Windows 7 :-)4-Oct 13:26
18589Maximgraham, I've been using 2.7.7 for a while and have never had any issues with the clipboard. I am running xp though, so its possible that something in windows 7 is causing this.4-Oct 13:17
18588LadislavYes, I wrote PIF, and inspired Carl to write CASE, I guess. Later on, I renamed PIF to CASE for compatibility. (and because CASE is a better name than PIF)4-Oct 0:09
18587GreggAh, I missed the negative sign, and forgot that Rambo did that.3-Oct 20:13
18586GrahamHasn't passed Gabriele's spam filter3-Oct 20:12
18585Grahamno, it's negative meaning it has not been reviewed yet3-Oct 20:12
18584GreggHmm, rambo only goes to 4402 for me here. Most recent doesn't show your ticket.3-Oct 20:11
18583GrahamRAMBO Ticket #-47793-Oct 20:08
18582GreggAnd thanks to Ladislav for PIF/CASE.3-Oct 20:08
18581GreggYeah, thanks for testing that.3-Oct 20:08
18580GrahamI'd better log this to rambo3-Oct 20:04
18579Grahamstarted up view 2.7.6, pasted to clipboard and can't read in 2.7.7 again.3-Oct 20:03
18578GreggCould be as simple as a change that tried to handle errors better and now fails for some reason.3-Oct 20:01
18577GreggOnly RT can say, unless a changelog is posted somewhere.3-Oct 20:01
18576GrahamI wonder what happened to the clipboard handling...3-Oct 20:00
18575GreggInteresting, and very good to know.3-Oct 19:59
18574GrahamWindows 7 prof3-Oct 19:59
18573Grahamworks on >> rebol/version == 2.7.6.3.13-Oct 19:59
18572Grahamfails on >> rebol/version == 2.7.7.3.13-Oct 19:58
18571GrahamAhh...... !!3-Oct 19:58
18570GreggWhat OS and what REBOL version?3-Oct 19:58
18569Grahamok, let me raise up an old core3-Oct 19:57
18568GreggAltMe is built against an older core.3-Oct 19:57
18567GrahamI was just copying from Chrome's address bar .. and also writing to the clipboard using core.3-Oct 19:57
18566Grahamif the clipboard were screwed .... then Altme wouldn't see it either??3-Oct 19:56
18565GreggWhat program are you writing data to the clipboard with?3-Oct 19:56
18564GrahamNo, I don't3-Oct 19:54
18563GreggDo you have any kind of clipboard monitoring software installed?3-Oct 19:54
18562GrahamI can paste this: test from Rebol, but can not paste into a new instance of View3-Oct 19:54
18561GrahamCorrection, I can write to the clipboard:// and paste into other apps, but Rebol is seeing nonthing there.3-Oct 19:53
18560GreggI think this is also what messes up AltMe's clipboard behavior at times.3-Oct 19:52
18559GreggREBOL sometimes seems to get confused if there is data on the clipboard, possibly related to the format of the clipboard data. Writing can fail at times too IME. Clearing the clipboard before writing usually solves the problem for me.3-Oct 19:52
18558GrahamIf I write to clipboard://, nothing is there either ...3-Oct 19:52
18557GrahamI can paste from the browser to notepad, and other apps, and it's just text, but .... the clipboard shows empty. The problem will go away if I reboot though.3-Oct 19:50
18556GrahamDoes anyone else experience the inability to read the clipboard ?3-Oct 19:49
18555GreggAll roads lead to Ladislav.3-Oct 19:48
18554GrahamYep ... !3-Oct 19:48
18553Gregg:-)3-Oct 19:47
18552GreggThat's Ladislav's PIF, just renamed.3-Oct 19:47
18551Grahamlooks like PIF!3-Oct 19:47
18550GreggThanks Graham!3-Oct 19:46
18549GrahamI don't know where this came from:

case: func [ [throw catch] args [block!] /local res ] [ either unset? first res: do/next args [ if not empty? args [ ; invalid guard throw make error! [script no-arg case condition] ] ] [ either first res [ either block? first res: do/next second res [ do first res ] [ ; not a block throw make error! [ script expect-arg case block [block!] ] ] ] [ case second do/next second res ] ] ]

3-Oct 19:45
18548Gregg1.2.473-Oct 19:44
18547Grahamhow old is old?3-Oct 19:44
18546GreggLadislav's PIF is my first stop.3-Oct 19:44
18545GreggDoes anyone have a well-tested mezz version of CASE handy for use with older REBOL cores?3-Oct 19:42
18544IzkataOr copy on any change, rather than on assign, as Java does with String1-Oct 20:57
18543BrianHAgreed. Though not many other languages always copy on assign - that's a relatively new habit.1-Oct 18:57
18542Maximfor the record (for the other people reading, which might not be as fluent in the more low level aspects of the core)..

I just want to note that your comment about thread safety doesn't only apply specifically to the /into...

It applies to *all* series usage in REBOL 3 since they are mutable and MANY functions modifiy series "in-place".

Other languages always copy on assign so its not as big an issue as in REBOL.

1-Oct 18:28
18541BrianHOf course task-safety isn't a problem for most R2 code, but then neither does R2 have natives with /into. Some of the new mezzanines though.1-Oct 18:07
18540Steeveyeah indeed1-Oct 18:06
18539BrianHThe downside of the /into option is that you have to be careful when using it or your code won't be task-safe. Your multiple references to a block that can change scenario is an example that can quite easily lead to task-unsafe code, for instance. But /into is great for micro-optimization and local code simplification, as long as you are careful to not modify shared structures without coordinating tasks.1-Oct 18:04
18538BrianHSounds interesting. I know that CHANGE/part is the real fundamental operation, but that needs an additional parameter and would require renaming the option - /into isn't an appropriate name for that operation. But I don't think it would have been implemented in that case, and having it be a direct CHANGE would definitely not have been accepted because /into is mostly used to replace chained INSERT and APPEND operations.1-Oct 18:00
18537Steeveabout reduce/into b b It allows to keep several references of the same block without the need to reassign them when the block is reconstructed. But currently, we can't avoid the block expansion because the data are inserted instead of beeing replaced (which would be more useful to my mind). Then, if internaly it's faster to do a copy, I don't care while it's not recycled by the GC (for the reasons I mentioned previously).1-Oct 17:41
18536Steeve* I know1-Oct 17:33
18535SteeveAbout the /into refinement. I don't bother if internaly, a copy is done or not, while it's faster and memory safe (the block must be freed immediatly not by the GC) The GC used to have some memory leaks and was reacting too late to be useful (especialy in apps with a GUI). I now it's better now (thanks to recycle/ballast).1-Oct 17:32
18534Izkatait was so that new memory didn't need to be allocated in this expression, and the old didn't need to be garbage collected:

b: reduce b

1-Oct 17:16
18533Maximwell IIRC Steeve had done tests and it was much faster... so something is being saved.1-Oct 16:22
18532Ladislav"this allows to save on an uneeded additional copy." - if you are referring to the

reduce/into b b

expression, Max, then your assumption is wrong, this cannot save an unneeded additonal copy

1-Oct 8:31
18531Maximwhen we generate blocks on the fly, we sometimes need evaluation to occur at a later stage. this allows to save on an uneeded additional copy. (which can be taxing on the GC when blocks are large)30-Sep 13:55
18530BrianHI definitely agree with that. I can't figure out a use for that code pattern, at least at first glance.29-Sep 23:24
18529Ladislav...neither it is really useful, in my opinion27-Sep 23:26
18528LadislavI specifically had objections against the

reduce/into b b

expression, which cannot be done efficiently without copying

27-Sep 23:24
18527Ladislav"REDUCE/into and COMPOSE/into were actually worth adding" - no problem with that, what I was saying, though, was something else27-Sep 23:22
18526BrianHHenrik had a use case for DEDUPLICATE, though that was when he thought he could eliminate the copy, and actually wanted to change UNIQUE to be modifying instead. It's not a common enough use case to make it into the core functions, but there is a mezzanine for it in the CureCode ticket.27-Sep 21:44
18525BrianHI suggested REDUCE/into and COMPOSE/into, and found them to be immediately useful. I don't know why UNIQUE/into is being suggested, its use case.27-Sep 21:36
18524BrianHThe main reason that UNIQUE isn't used is because it is not very useful: It is easier to make sure that the series is unique in the first place. The other "set" functions like INTERSECT, DIFFERENCE and EXCLUDE are used more often, even though they do the same copies as UNIQUE, using the same hashing method.27-Sep 21:34
18523BrianHREDUCE/into and COMPOSE/into cut down 2 copies to 1. They don't eliminate copies altogether.27-Sep 21:30
18522BrianHLadislav, REDUCE/into is used to eliminate a temporary series allocation in the common INSERT REDUCE and APPEND REDUCE patterns. It is used in mezzanine code, and does in fact reduce memory allocation overhead. Hate to break it to you, but REDUCE/into and COMPOSE/into were actually worth adding. Sorry.27-Sep 21:29
18521Anton(Oops, the last three examples should begin: usepath p 'root/.... )27-Sep 15:19
18520AntonAll good fun.27-Sep 15:16
18519AntonAnd here's an idea which may make the usage simpler: Write a function USEPATH, used like this:

values: [1 [dos [new 0]]] p: 'values/1/dos/new usepath p [p: p + 1] ;=== (values/1/dos/new: values/1/dos/new + 1) values ;== [1 [dos [new 1]] or perhaps, achieving the same result:

usepath p 'v [v: v + 1]

where v is the value SELECTed by the last element in the path (so you can choose a different variable name). or even:

usepath p 4 'v [v: v + 1]

where 'v is set to refer to the value of the 4th element ('new) in the path. so we can refer to any path element by its number, and so this would achieve the same:

usepath p 3 'v [v/new: v/new + 1] ;=== (values/1/dos/new: values/1/dos/new + 1) and even crazier:

usepath p 'root/pid/fs/flag [flag: flag + 1]

where the second path elements (all word!s) reference the values actually SELECTed in p, so these are all equivalent: usepath p 'values/pid/fs/flag [fs/dos: flag + 1] usepath p 'values/pid/fs/flag [fs/dos: fs/dos + 1] usepath p 'values/pid/fs/flag [root/pid/fs/flag: flag + 1]

27-Sep 15:06
18518AntonJust to remind, DideC's example had:

values: [ 1 [dos [new 0 modified 0 deleted 0] fic [new 0 modified 0 deleted 0]] 2 [dos [new 0 modified 0 deleted 0] fic [new 0 modified 0 deleted 0]] ]

27-Sep 15:06
18517Antonsforpath: func ["Evaluate a path similar to the builtin path evaluation, except number elements SELECT (rather than PICK)." path [path!] action [function! block!] /local e v c ][ v: get path/1 ; The path is assumed to begin with a word, so get its value. while [not tail? path: next path][ ; Step through the path to inspect each of its elements. c: v ; Store the current value before SELECTing into it. e: pick path 1 ; The current element. ;print [mold :e mold type? :e] if get-word? :e [e: get e] case [ number? e [v: select v e] ; SELECT this number element. (Paths normally PICK number elements.) word? e [v: select v e] ; SELECT this word element (as paths normally do). ] ] ;?? e ?? v ?? c ; Process the last element. if block? :action [action: func [c e] action] action c e ] ; Test values: [1 [dos [new 0]]] sforpath 'values/1/dos/new [c/:e: c/:e + 1] ; <- DideC's INC-COUNTER function could be implemented simply using this.27-Sep 14:16
18516AntonBut oh yeah, I wrote this experimental function last night.27-Sep 14:15
18515AntonIt makes me a bit sad that we haven't found a way to get what I wanted.27-Sep 13:06
18514AntonGeomol, I thought about it a bit more and realized what you said made good sense.27-Sep 13:05
18513GeomolAnton, I think, it's a "ground rule" in Carl's design of the language, that everything entered into the parser are datatypes (or series of datatypes). I can't think of anything with semantic meaning, that is not a datatype, when we talk REBOL. The language is recognized by it's minimalistic syntax. That's why I call it a "ground rule".

I think, it's legal to call REBOL a sequence of datatypes. It's maybe more precise than calling it a programming language (also because it's so different from traditional programming languages).

And then, yes, he has added newline markers to e.g. blocks. But they have no semantic consequence.

27-Sep 12:27
18512Ladislav"Of course, people might still do it, thinking they're optimizing." - you nailed it27-Sep 7:18
18511GreggI guess I just don't care enough about how hard I make the GC work.27-Sep 7:16
18510GreggIt doesn't make sense to reduce/into the same series, but that's not the intended purpose. Or am I missing something? Of course, people might still do it, thinking they're optimizing. :-\27-Sep 7:15
18509Ladislavbut the most crazy is not that reduce/into b b "looks crazy", but that it is unneeded, and *very* inefficient, unless implemented using copying27-Sep 7:06
18508GreggI've never had a need for reduce/into or unique/into. The optimizer in my brain says reduce/info could be useful, but the rest of my brain thinks the lure of possible optimizations will create internal strife with said optimizer. :-) I do have an /into refinment on my COLLECT func, and the standard COLLECT does as well, but my goal there was for convenience is building up results, not optimization.27-Sep 7:01
18507ForkRebol looks crazy to most people regardless. To my midn, if Rebol has so far avoided a convention like /NO-COPY on these other routines in favor of /INTO, then consistent and learnable novelty trumps some organic evolution of refinements and wording in the core.27-Sep 5:48
18506Ladislav(I never felt like using such things)27-Sep 5:25
18505Ladislavthese reduce/into b b and unique/into b b make me wonder, whether the people suggesting it really find such crazy code useful?27-Sep 5:25
18504ForkLadislav/BrianH: so doesn't that imply that the UNIQUE/INTO variant would be more useful as a native than UNIQUE/NO-COPY? (I'm not sure how a temporary state of a series of length 2N which has N discarded is worse than 2 series of size N in which one of those series is discarded.)27-Sep 3:18
18503Grahamooops ... wrong group27-Sep 2:47
18502GrahamLooks like the python FBP is http://www.kamaelia.org/Home.html27-Sep 2:47
18501GrahamI guess the argument about existing references then also applies to 'unique27-Sep 2:12
18500GrahamRegarding the above, is there a way to reassign and take exisiting references with you? Or, is this a lack of pointer manipulation?27-Sep 1:41
18499Ladislav{See UNIQUE. This function is not widely used in my apps, just because of that. Useless, because when we deals with huge series, we don't want to pay the COPY cost.} - while this looks like a reasonable argument at the first sight, it actually isn't. The reason why is based on the way how UNIQUE is (and has to be) implemented. You cannot gain any speed worth that name by allowing an implementation doing the "UNIQUE job" in place.27-Sep 1:33
18498ForkOh well, I dunno. It's too hot here right now to think at all. 92 indoors in the shade.26-Sep 22:14
18497Fork(May have misunderstand what you meant about the algorithm needing the original array and a temporary buffer the size of the output, as well as the output.)26-Sep 22:13
18496ForkWould doing the /INTO at the end of the series make it easier for the memory allocator to reclaim the space after the remove?26-Sep 22:10
18495ForkDidn't you say that UNIQUE has to copy the series anyway? What's the difference?26-Sep 22:09
18494BrianHFork, your method would add the additional series allocation to the series itself, temporarily doubling its size (at most). And then the reallocated series would stay that size in memory even after DEDUPLICATE returns. So overall, worse.26-Sep 21:44
18493BrianHWe could only add one behavior for the /into option, and the insert behavior was the most basic.26-Sep 21:41
18492SteeveIt comes to my mind that reduce/into should not behave like inserting data but changing them. Changing data if it's it's at the end of the container will simply add them. But if it's at the head of the container, it will remplace them intead. Probably more usefull, than the current behavior.

so that >> reduce/into data data would simply do the job we all expecting. To reuse the same block. A reduce in place (rest in a peace)

26-Sep 20:57
18491Fork/INTO is kind of novel and catchy, in terms of some of the optimization scenarios it allows for. Making variants like "/NO-COPY" winds up looking like Rebol is doing a bad job of conventions like REDUCE vs REDUCE! ... as opposed to playing a whole different game.26-Sep 20:53
18490Steeveah! reduce in place. But what a pain (in the ...)26-Sep 20:45
18489ForkModifying REDUCE variant based on REDUCE/INTO, as a general pattern, just wondering what the data loss is that BrianH is referring to.26-Sep 20:41
18488Steeveuh ????26-Sep 20:39
18487ForkWorks for DEDUPLICATE also, no?26-Sep 20:38
18486Fork>> reducificate: func [value] [either series? :value [head remove/part reduce/into value value tail value] [reduce :value]]26-Sep 20:37
18485Janko(((( I know you don't agree with me, but I want a VM level way to define pure functions (that are guaranteed they can't change anything outside itself). Big future deal in rebol to me is in runtime code generation to express things and *code mobility* and there can't be any real mobility if the code I get can "get over the wire" can do anything to my system ))))26-Sep 20:32
18484BrianHTime will tell. Like it or not, REBOL is primarily built around mutating functions, except for functions that work on immutable values like integers. Most of the non-mutating functions we have are either built on their mutating counterparts in mezzanine, or are options of those functions. In a language with mutable values, mutating functions are the base. Functional-language fans tend to not like this (and when we start really implementing task-safe code they can say "I told you so!"). However, mutability can have advantages too, mostly in memory usage and performance, so it's a tradeoff.26-Sep 19:41
18483BrianHThe /into option wasn't added to many applicable natives, just the two that generate the most data in REBOL: REDUCE and COMPOSE. That might be a "biggest bang for the buck" thing, or maybe we just haven't gotten around to it yet. Or it might be a big hassle to add /into to a native, so to get it done you need to justify it with use cases.26-Sep 19:36
18482BrianHNo, that probably wouldn't work because you need the intermediate series so you don't have data loss. So, no use case so far.26-Sep 19:34
18481BrianHUNIQUE/into, good idea. DEDUPLICATE would use UNIQUE/into internally, but I can't think of any other use case. I'm sure others could.26-Sep 19:23
18480SteeveThere is absolutly no gain to copy by default. As Gregg stated: "you can easily COPY if you want, but it's hard to go the other way". I'd say more: Default copies induces overheads you can't discard most of the time. See UNIQUE. This function is not widely used in my apps, just because of that. Useless, because when we deals with huge series, we don't want to pay the COPY cost.26-Sep 18:30
18479GreggI don't think the Ruby ! sigil is particularly meaningful, so I wouldn't vote for that.

While having complete consistency might make for a more pure and mathematically beautiful language, I don't think that is REBOL's goal. REBOL's design has elements that exist to make things simpler and more obvious. You could argue that complete consistency would do that, but if you look at history, that's not the case.

"the argument that sort modifies because you can always copy first is met by the retort that you can always assign afterwards" - You can always assign, but if you have other references to that series, they wouldn't see the change. This can also cause unintended side effects of course, which is the risk of modifying, but that's part of REBOL too. :-\

We'll never please everyone. I'm OK with the current SORT and set-operation behavior.

26-Sep 18:21
18478AndreasI also would love more internal consistency between mutating and non-mutating versions (and I'd personally like to have non-mutating versions be the default for all functions). But realistically, this kind of simplification will never be really an option for future REBOL development, I fear.26-Sep 12:08
18477Steevemagic :)26-Sep 8:48
18476Nicolaswow26-Sep 8:47
18475Steevecall: func [file] compose [(:call) quotate quotate to-local-file file]26-Sep 8:45
18474Grahamuse [ n ][ n: :now set 'now func [][ n + 1]]26-Sep 8:17
18473Nicolasold: context [call: get in system/words 'call] call: func [file] [old/call quotate quotate to-local-file file]26-Sep 8:17
18472NicolasThis works, but I can't get it into a redefine function.26-Sep 8:17
18471Nicolasthis doesn't work obviously. but do you get my meaning?26-Sep 8:14
18470Nicolase.g. call: func [file] [system/words/call quotate quotate to-local-file file]26-Sep 8:13
18469NicolasDoes anyone know how to redefine words?26-Sep 8:12
18468NicolasI'll just use call2 then.26-Sep 8:11
18467Nicolas** Script Error: Feature not available in this REBOL26-Sep 8:04
18466GrahamExcept 'run was only implemented in IOS26-Sep 8:03
18465GrahamPerhaps you want 'run and not 'call ?26-Sep 8:03
18464HenrikI don't agree to copy on sort.26-Sep 7:59
18463Nicolasquotate: func [str][rejoin [{"} str {"}]]26-Sep 7:56
18462Nicolasto get around it I use this function call2: func [file][call quotate quotate to-local-file file]26-Sep 7:56
18461Nicolashere's one %/d/music/Astor%20Piazzolla/Astor%20Piazzolla%20-%20Adios%20nonino%20%28live%29.mp326-Sep 7:55
18460Nicolasactually the parentheses should be %28 and %2926-Sep 7:53
18459Nicolasbut doesn't call it26-Sep 7:52
18458Nicolasreturns zero26-Sep 7:52
18457Grahamand what happens for you?26-Sep 7:51
18456Nicolascall %/d/something%20with%20(parentheses).mp326-Sep 7:48
18455Grahameg. ?26-Sep 7:46
18454NicolasDoes anyone else have trouble calling a file that has parentheses in it?26-Sep 7:33
18453Grahamperhaps it's a feeling that refinements should be used for passing new arguments than modifying behaviour?26-Sep 6:58
18452ForkSome thought process in Rebol design didn't make "ARITHMETICATE" or some variant of REDUCE which is modifying on its value target. Instead, it was decided that REDUCE/INTO would be more interesting. I'm just wondering what optimization logic makes DEDUPLICATE more interesting than UNIQUE/INTO... ?26-Sep 6:52
18451ForkAnyway, the issue is about the program expressing the intent of the programmer and letting the system do the smartest thing under the hood given the understanding of what the programmer wanted, for the common cases.26-Sep 6:44
18450ForkWhether sort in place is more expensive or not depends on the fundamental operations upon which sort is built. (This makes interview questions fun when people "know" the answers, because you say "oh. well let's say you're on an architecture where a memory allocation costs 1000 times more than a swap"... :P)26-Sep 6:43
18449Grahamso, modifying the original series is likely to be a convention and not an optimization26-Sep 6:40
18448GrahamSo, tell me .. sort in place is more expensive than not, so another series is already created somewhere ...26-Sep 6:39
18447ForkHence the catch-phrase "Inspired by theory, driven by practice." Of course, then the question comes up of "whose practice?" when releases are being timed to Amiga announcements etc.26-Sep 6:36
18446ForkI think that Rebol already has the "i before e but not after q and sometimes z" philosophy, in that there are forces driving it that are something of the nature of what drives natural language design. Purely consistent languages which have no special adaptations to the "messy" world don't really need to be designed, they exist mathematically already. They are more discovered than made.26-Sep 6:35
18445Grahamthe argument that sort modifies because you can always copy first is met by the retort that you can always assign afterwards26-Sep 6:33
18444Grahamconsistency leads to a lower cognitive load for the programmer26-Sep 6:31
18443ForkWhy not follow your INTO convention? Couldn't you make UNIQUE/INTO?26-Sep 6:24
18442ForkThe learnability of consistency vs. the beauty of making the common cases and idioms look elegant. But are those looks deceiving? English sure is a mess... but people find it effective.26-Sep 6:21
18441Fork(In my currently-still-very-limited Ruby tinkering, I have liked this convention--and in fact, sort of wished there were some way of it being more than just a convention, but reflected in a contract which generated both the modifying and non-modifying variant of an operation.)26-Sep 6:13
18440ForkIf one could turn back time, I wonder if {!} for types would be better served by some other symbol like {^} , and Rebol could have UNIQUE! (modifying) vs. UNIQUE (make a copy) in the style of Ruby and company. "Verbs modify" isn't consistent, since REDUCE or COMPOSE don't modify while SORT and REVERSE do.26-Sep 6:12
18439GrahamI prefer the symmetry

series: sort series

instead of one doing one , and not the other

26-Sep 5:16
18438GrahamCarl says it has to make a new series anyway26-Sep 5:15
18437Grahamseries: unique series26-Sep 5:14
18436ForkThis isn't a serious question. Devil's advocacy, or what you might call it. But given Rebol's insistence that "/only" is a somewhat opaque modifier speaking about whether the routine in question does its "extra" thing or not... wouldn't "unique/only" be a way of saying "sort the array in place only, don't do the make copy step"?26-Sep 5:11
18435BrianHHence the quotes.26-Sep 2:23
18434GrahamBTW, the term set function is confusing .. perhaps use the term sets function26-Sep 2:11
18433Grahamwell, we don't have the source code to 'sort to know whether the sort creates a new copy or whether it sorts in situ ... so no idea whether there is a penalty or not26-Sep 2:08
18432Grahamso that all act like one would expect a pipe function would work .. least suprise here26-Sep 2:06
18431GrahamI think i'd prefer consistent behaviour and not have any modifying function of the ones discussed26-Sep 2:05
18430BrianHAll the set functions have to allocate a new series internally for hashing, at least for large series (cutoff not documented). This would also be the case for modifying versions of all of the set functions - you wouldn't save a copy.26-Sep 1:55
18429BrianHCheck here for a proposal for a modifying counterpart for UNIQUE: http://curecode.org/rebol3/ticket.rsp?id=1573 The recently created word DEDUPLICATE is the closest single English word for the concept. Note that it will still copy internally, because the UNIQUE algorithm requires a copy to work (it makes a hashed copy to determine uniqueness).26-Sep 1:52
18428Graham"Most of the time" .. from where were these metrics derived?26-Sep 1:50
18427BrianHA function to change a series to a "set".26-Sep 1:45
18426Grahamand 'unique is .. ?26-Sep 1:44
18425BrianHThe exception is the "set" functions that are supposed to make series act like unique sets. Most of the time people need copies when working with set functions. We had a big discussdion about this earlier.26-Sep 1:43
18424GrahamWherein lies the rhyme or reason?26-Sep 1:40
18423GrahamSo, why does 'unique not modify the original series?26-Sep 1:40
18422BrianHThere are many functions like that in REBOL, which act that way for the same reason. Most of the functions with a /copy option are like that.26-Sep 1:38
18421GreggBecause you can easily COPY if you want, but it's hard to go the other way. That's the general thinking as I understand it (and agree with most of the time).26-Sep 1:02
18420Grahamhas anyone done any testing on whether the speed is that much different?25-Sep 23:58
18419Andreas... bla bla bla ... speed ... bla bla bla25-Sep 23:56
18418GrahamWhy does sort modify the source ? What's the rationale for making a function that acts to transform data also modify the source?25-Sep 23:52
18417AntonGabriele, ahh for syntactic sugar...25-Sep 16:15
18416GabrieleAnton: DideC's question requires a temporary variable because paths require a temporary variable (first element must be word), not because select does. If paths could start with a paren, for example, you could write:

(select values 1)/x/y: 10

But this is only a problem because we like the syntactic sugar, if you write that as functions all problems go away. I'm not sure if it's worth adding more syntactic sugar or not at this point...

25-Sep 7:58
18415AntonGeomol, you have not explained why you think the rule you mention is a "ground rule" (by which I suppose you mean a fixed rule). I read your comment simply as saying that you are resistent to changing a rule, but you don't explain why. Of course, once you accept that the rule cannot be changed, the first part of your comment flows logically from it. That's not good enough for me, though. The only argument that I can imagine you might be putting forward here is that it's better to keep things simple, rather than add any complexity. I am proposing to add some complexity to the language implementation which can simplify the use of the language, and, for me, it appears to be worth it. Rebol internals have made themselves visible (eg. end! == first first system/words) which I think is used to terminate blocks or lists or some other container datatype (perhaps path!), and also there are the hidden new-line markers in blocks and lists (but not in hash!). So, ok, a new "path-escape marker" datatype may need be created to implement my proposal, but it doesn't have to be exposed to user space.24-Sep 17:31
18414AntonGabriele; About the temporary variables; if you go back to 17-Sep, in DideC's original question, his inc-counter function took a path as argument, but he had to introduce a temporary variable 'p so he could SELECT the integer path member. (And a few other people suggested functions doing the same thing.)

Also, note once again -> I did not propose to change the way paths currently work with integers. I proposed to *add* a new way to process integer path members. This new way does not subtract from any current functionality of any significance (that I've yet noticed, anyway).

24-Sep 16:51
18413AntonBrianH, that cuts it down a little bit. (But would I be happy with that? I'm not sure...)24-Sep 16:36
18412DideCSorry wrong groupe.24-Sep 11:16
18411DideCDo you know if it's better24-Sep 11:16
18410GabrieleOldes, if it's about speed, this is going to be even faster:

loop 1000000 bind [e: e + 1] a/b/c/d

24-Sep 9:27
18409GeomolAnton, you may not have proposed a new datatype, but I think, the consequence of your proporsal would be a new datatype. I think so, because everything the REBOL parser knows, are datatypes. Some datatypes are series of datatypes, like blocks, parens and paths. I feel, it's a ground rule, that everything separated by slashes in a path, are by themselves datatypes.24-Sep 8:17
18408OldesBut if Carl will agree with the lit-integer, proposal I'm not agains that.23-Sep 10:51
18407OldesWhen I talk about temp var usage, I mean this: >> a: context [b: context [c: context [d: context [e: 1]]]] >> tm 1 [loop 1000000 [a/b/c/d/e: a/b/c/d/e + 1]] == 0:00:00.829 >> tm 1 [t: a/b/c/d loop 1000000 [t/e: t/e + 1]] == 0:00:00.57823-Sep 10:47
18406GabrieleHmm, isn't it the other way around? paths need to start with a word, so you need a temporary variable; select's arguments have no limitation, so you don't need temporary variables.

Also, what about people who use the current way paths work with integer? It's bad to use select instead of path, but it is good to use pick instead of path? why?

23-Sep 10:06
18405BrianHAs long as you are careful about your build process (or don't use one) you can use serialized syntax for literal maps: #[map! [a 1]]22-Sep 22:33
18404Maxim(and faster)22-Sep 15:40
18403AntonI'm not interested in all the possible cases where using temporary variables isn't so bad (or even where it's better). I'm interested in those cases, which do come up from time to time, where using temporary variables is uncomfortable, and using a path directly to get to what I want would be much better (indeed, smoother).22-Sep 15:32
18402Pekras for me - I hate SELECT :-)22-Sep 13:31
18401Pekrgoing via the variable disturbes your smooth flow of thoughts :-) we want as much of function chaining, as possible :-)22-Sep 13:30
18400Oldesbtw.. in many case using temporaly variables is not so bad and may have better results than multiple deep path queries.22-Sep 13:16
18399OldesYou can always use TO-MAP:)22-Sep 13:13

Return to Index Page