Great stuff from both of you - I am thinking of changing my INI file handling code to one of these methods (where I have a hash of hashes so that a section value is really itself an associative array). But Elan, what do you mean when you say that there is a problem with function code duplication using the object approach? I haven't used a lot of Rebol objects yet, but my OOP experience tells me (yes I know I'm supposed to forget it about that!) that there is only one instance of code for all objects based on a base template. TIA, Rodney -----Original Message----- From: [EMAIL PROTECTED] [mailto:[EMAIL PROTECTED]] Sent: Thursday, September 14, 2000 1:38 PM To: [EMAIL PROTECTED] Subject: [REBOL] Associative data store Re: Hi Joel, Nice. you wrote: >Critiques and comments welcome! With respect to the line: > new: func [/local r] [r: make assoc [] r/clear r] I think it would be safer to use self instead of assoc new: func [/local r] [r: make self [] r/clear r] ^^^^ 2. An alternative: assoc: [keys [] values []] is-assoc?: func [assoc [block!]] [ all [equal? length? assoc 4 find assoc 'keys find assoc 'values] ] contains-key?: func [assoc [block!] key [any-type!] ] [ all [is-assoc? assoc find assoc/keys key] ] assoc-add: func [assoc [block!] candidates [block!] /local found] [ if is-assoc? assoc [ foreach [key value] candidates [ either found: contains-key? assoc key [ insert at assoc/values index? found value ][ insert assoc/keys key insert assoc/values value ] ] return true ] return false ] assoc-get: func [assoc [block!] key [any-type!] /local found] [ if found: contains-key? assoc key [ return pick assoc/values index? found ] return none ] >> phonelist: copy/deep assoc == [keys [] values []] >> assoc-add phonelist [Bill "555-1111"] == true >> assoc-add phonelist [Al "555-2222"] == true >> assoc-add phonelist [George "555-3333"] == true >> assoc-add phonelist [Dick "555-4444"] == true >> assoc-add phonelist [Jane "555-3322" Judy "555-2233"] == true >> assoc-get phonelist 'Bill == "555-1111" >> assoc-get phonelist 'Dick == "555-4444" >> assoc-get phonelist 'George == "555-3333" >> assoc-get phonelist 'Jane == "555-3322" >> assoc-get phonelist 'Judy == "555-2233" >> assoc-get phonelist 'Al == "555-2222" >> foreach who sort copy phonelist/keys [print [who assoc-get phonelist who]] Al 555-2222 Bill 555-1111 Dick 555-4444 George 555-3333 Jane 555-3322 Judy 555-2233 Looks to me like it accomplishes pretty much the same thing > separation of key/value spaces without the additional overhead of an object (function code duplication for each list). In addition I see the advantage of being able to effortlessly add multiple items by including them in a block (batch adding ;-). At 04:01 PM 9/14/00 -0500, you wrote: >The proposed implementation below addresses separation of key/value >spaces and tries to take advantage of REBOL built-ins for performance >wherever feasible. Critiques and comments welcome! > >-jn- > >===============(begin code listing)================== >REBOL [ > Title: "Minimal Associative Data Store" > File: %assoc.r > Date: 14-Sep-2000 > Author: "Joel Neely" > Purpose: { > Quick, minimal implementation of a data store that > associates arbitrary values with (string!) keys. > } >] > >assoc: make object! [ > _keys: copy [] > _vals: copy [] > clear: func [] [_keys: copy [] _vals: copy []] > clear?: func [] [empty? head _keys] > count?: func [] [length? _keys] > new: func [/local r] [r: make assoc [] r/clear r] > put: func [k [string!] v [any-type!] /local p] [ > either none? p: find _keys k [ > append _keys k > append _vals v > ][ > change at _vals index? p v > ] > v > ] > get: func [k [string!] /local p] [ > either none? p: find _keys k [ > none > ][ > pick _vals index? p > ] > ] > keys: func [] [copy _keys] >] >=================(end code listing)================== > >This (minimal) implementation can be used as follows: > >=================(begin transcript)================== >>> do %assoc.r >>> phonelist: assoc/new >>> phonelist/clear? >== true >>> phonelist/put "Bill" "555-1111" >== "555-1111" >>> phonelist/put "Al" "555-2222" >== "555-2222" >>> phonelist/put "George" "555-3333" >== "555-3333" >>> phonelist/put "Dick" "555-4444" >== "555-4444" >>> phonelist/get "Al" >== "555-2222" >>> phonelist/count? >== 4 >>> phonelist/keys >== ["Bill" "Al" "George" "Dick"] >>> foreach who phonelist/keys [print [who "^-" phonelist/get who]] >Bill 555-1111 >Al 555-2222 >George 555-3333 >Dick 555-4444 >>> foreach who sort phonelist/keys [print [who "^-" phonelist/get who]] >Al 555-2222 >Bill 555-1111 >Dick 555-4444 >George 555-3333 >>> privatelist: phonelist/new >>> privatelist/count? >== 0 >>> >>> foreach who head reverse sort phonelist/keys [ >[ print [who "^-" phonelist/get who] >[ ] >George 555-3333 >Dick 555-4444 >Bill 555-1111 >Al 555-2222 >>>==================(end transcript)=================== > >Enjoy! > >-jn- > >-- >; Joel Neely [EMAIL PROTECTED] 901-263-4460 38017/HKA/9677 >REBOL [] print to-string debase/64 decompress #{ > 789C0BCE0BAB4A7176CA48CAB53448740FABF474F3720BCC > B6F4F574CFC888342AC949CE74B50500E1710C0C24000000} > > > ;- Elan [ : - ) ] author of REBOL: THE OFFICIAL GUIDE REBOL Press: The Official Source for REBOL Books http://www.REBOLpress.com visit me at http://www.TechScribe.com
