Groups | Search | Server Info | Keyboard shortcuts | Login | Register [http] [https] [nntp] [nntps]


Groups > comp.lang.postscript > #2194

Re: map and higher order functions

Newsgroups comp.lang.postscript
Date 2015-02-27 00:59 -0800
References <20141030172728.0983c6bc@samara.DOMA> <95798773-17c6-41d3-8d80-06d1784a7e95@googlegroups.com> <20141102001537.515de3e5@samara.DOMA> <1cc8e78b-6698-4bab-b63c-9475cc63a5c3@googlegroups.com> <20141116013757.0dacc25d@samara.DOMA>
Message-ID <52999eef-98fd-429f-ad2d-e76b779edbed@googlegroups.com> (permalink)
Subject Re: map and higher order functions
From luser- -droog <mijoryx@yahoo.com>

Show all headers | View raw


On Saturday, November 15, 2014 at 6:38:00 PM UTC-6, Carlos wrote:
> [luser- -droog <mijoryx@yahoo.com>, 2014-11-15 00:43]
> [...]
> > There is a possible problem here. Since `bind` applies to all
> > subarrays, and the user-proc has been embedded directly into this
> > array.
> > 
> > instead of
> > 
> > >                 //proc exec
> > 
> > it might be better to do
> > 
> >                   //mydict /proc get exec
> > 
> > so the procedure is not directly embedded.
> > 
> > Applying `bind` would break code that tries to use operator names as
> > variables, like
> > 
> >     {
> >         /length 5 def
> >         length dup mul % length^2
> >         ...
> >     }
> > 
> > The executable name `length` in the second line would be replaced by
> > the postscript operator if `bind` were applied.
> 
> I didn't think of that. The problem is worse, because the string is
> tokenized at the time /map is executed, and by that moment the user
> could have already redefined some operators (presumably he wouldn't do
> that at library loading time).
> 
>     /length 5 def [ 1 2 3 ] { length add } map
> 
> So, basically, inside /map, the code surrounding "<userproc> exec"
> should be bound before any operator is redefined, but the "<userproc>"
> should be left as-is.
> 
> One solution can be to write the code as usual (not in a string), using
> placeholders for the objects. That way, it would be bound at definition
> time. When /map is called, the placeholders are replaced with the
> objects. Basically, doing the "({ //x }) token" thing by hand, just so
> everything that isn't a //name can be bound at definition time.
> 
> Here is a new version of map that uses that approach, plus two helper
> procedures:
> 
> % <array/string> <proc> map <new array/string>
> /map {
>     4 dict begin
>         /,proc exch def
>         /,arr exch def
>         /,res ,arr length
>              ,arr type /stringtype eq { string } { array } ifelse
>         def
>         /,i 1 array def
>         {
>             0 1 /,arr length 1 sub { % for
>                 dup /,i 0  3 -1 roll  put
>                 /,arr exch get
>                 /,proc exec
>                 /,res /,i 0 get  3 -1 roll  put
>             } for
>             /,res
>         } deepcopy dup currentdict replaceall
>     end exec
> } bind def
> 
> % copies array recursively
> % <array> deepcopy <new array>
> /deepcopy {
>     dup xcheck exch
>     dup length array copy
>     dup length 1 sub 0 exch 1 exch { % for       % a i
>         2 copy 2 copy get dup type /arraytype eq % a i a i e ?
>         { % ifelse
>             deepcopy put
>         }
>         {
>             pop pop pop
>         } ifelse
>         pop
>     } for
>     exch { cvx } if
> } bind def
> 
> % recursively replaces elements in <array> found in <dict>
> % <array> <dict> replaceall -
> /replaceall {
>     1 index length 1 sub  0 1  3 -1 roll { % for 0 1 length-1
>         3 copy  3 -1 roll  exch    % a d i d a i
>         get                        % a d i d e
>         2 copy known               % a d i d e ?
>         % ifelse
>         {                          % a d i d e
>             get                    % a d i v
>             3 index  3 1 roll      % a d a i v
>             put
>         } % else
>         {                          % a d i d e
>             dup type /arraytype eq % a d i d e ?
>             { exch replaceall }
>             { pop pop } ifelse
>             pop
>         } ifelse                   % a d
>     } for
>     pop pop
> } bind def
> 
> Carlos.
> --

I stumbled across an old one of mine. The file is
dated Dec 24 2012. This version is not safe to use
if any of its operators are not available by their
standard names at *execution time*, ie. this code
exhibits the problem that Carlos's code solves.
But it's shorter. :)

It also modifies the argument in-place. So if you
want a copy, make a copy. Delayed-binding, and such.

%!
%/exch{pstack exch}bind def 

%string proc  map  --  
%array proc  map  --  
/map{
    4 dict dup begin
    {/dic/proc/src}{exch def}forall

    0 1 src length 1 sub 
    (   
     {   
        //dic/i 2 index put 
        //src exch get 
            //proc exec
        //src exch //dic/i get exch put 
     }   
    )token pop exch pop 
    bind end for 
}def

[1 1 1]dup{1 sub}map ==
(---)== flush
(this_is_a_lowercase_string___ish)dup
{16#20 sub}map
==

Back to comp.lang.postscript | Previous | NextPrevious in thread | Find similar


Thread

map and higher order functions Carlos <angus@quovadis.com.ar> - 2014-10-30 17:27 +0100
  Re: map and higher order functions ken <ken@spamcop.net> - 2014-10-30 16:57 +0000
    Re: map and higher order functions Carlos <angus@quovadis.com.ar> - 2014-10-30 19:55 +0100
      Re: map and higher order functions ken <ken@spamcop.net> - 2014-10-31 12:17 +0000
  Re: map and higher order functions Ross Presser <rpresser@gmail.com> - 2014-10-30 20:30 -0700
    Re: map and higher order functions Carlos <angus@quovadis.com.ar> - 2014-11-01 23:58 +0100
  Re: map and higher order functions luser- -droog <mijoryx@yahoo.com> - 2014-10-30 22:56 -0700
    Re: map and higher order functions Carlos <angus@quovadis.com.ar> - 2014-11-02 00:15 +0100
      Re: map and higher order functions luser- -droog <mijoryx@yahoo.com> - 2014-11-15 00:43 -0800
        Re: map and higher order functions Carlos <angus@quovadis.com.ar> - 2014-11-16 01:37 +0100
          Re: map and higher order functions luser- -droog <mijoryx@yahoo.com> - 2014-11-21 00:17 -0800
          Re: map and higher order functions luser- -droog <mijoryx@yahoo.com> - 2015-02-27 00:59 -0800

csiph-web