# concatenative thread on "lambda the ultimate"

## stevan apter — 2005-08-16 11:20:37

    the standard moves and counter-moves:

    http://lambda-the-ultimate.org/node/view/900

## William Tanksley, Jr — 2005-08-17 04:05:04

    stevan apter <sa@...> wrote:

     > the standard moves and counter-moves:

    > http://lambda-the-ultimate.org/node/view/900

     Hmm. I'm surprised to see a long argument about how painful using the

    stack is, and nobody mentioning the concept of dataflow. The "stack

    shufflers" aren't merely a low-level hinderance; they're also :) a

    high-level expression of explicit dataflow control. People claiming

    that concatenative languages are low-level because the expose the

    stack haven't noticed that the stack is invisible... Not exposed. It's

    implicit.

    -Billy

## Chris Double — 2005-08-17 04:15:54

    On Tue, 16 Aug 2005 21:05:04 -0700, "William Tanksley, Jr"

     > People claiming that concatenative languages are low-level because the

    > expose the stack haven't noticed that the stack is invisible... Not

    > exposed. It's implicit.

     Most of the complaints seem to center around the stack words not being

    part of the problem domain, so make the code harder to read/understand.

    It is therefore low level (by their definition). I don't really disagree

    with their point of view, as when doing lots of stack manipulation it

    can seem low level at times.

    Chris.

## William Tanksley, Jr — 2005-08-17 04:41:22

    Chris Double <chris.double@...> wrote:

     > On Tue, 16 Aug 2005 21:05:04 -0700, "William Tanksley, Jr"

    > > People claiming that concatenative languages are low-level because the

    > > expose the stack haven't noticed that the stack is invisible... Not

    > > exposed. It's implicit.

    > Most of the complaints seem to center around the stack words not being

    > part of the problem domain, so make the code harder to read/understand.

    > It is therefore low level (by their definition). I don't really disagree

    > with their point of view, as when doing lots of stack manipulation it

    > can seem low level at times.

     It certainly can. I admit it. But it's not, in general. In general,

    you're making your dataflow explicit -- and your dataflow IS part of

    your problem (not just a low level detail). Yes, it makes you think. I

    claim that the thinking is good for you and for your problem. Once you

    find a dataflow that looks good in code, it'll also run well.

    It's not low-level -- but it's perfectly compatible with it, unlike

    most other concepts the high-level languages seem to like.

     > Chris.

     -Billy

## Chris Double — 2005-08-17 05:01:47

    On Tue, 16 Aug 2005 21:41:22 -0700, "William Tanksley, Jr"

    <wtanksleyjr@...> said:

     > Yes, it makes you think. I claim that the thinking is good for you and

    > for your problem. Once you find a dataflow that looks good in code,

    > it'll also run well.

     I very much agree with this. When programming in Factor I think about

    how to organise the code a lot more than in other languages. And as a

    result I often get better, more correct, code out of it.

    Chris.

    --

      Chris Double

      chris.double@...

## sa@dfa.com — 2005-08-17 19:10:32

    i've been meaning to do this for a while.  playing with jot

    pushed me to do something about it.

    in the languages we've been discussing, everything is a unary

    function: stack -> stack.  in what i'm calling 'x', everything

    is a unary function: function -> function.

    the initial state is the identity function.

    a literal is a function which takes the state and produces

    a new function.  that function, when evaluated, evaluates

    the state it took as an argument, which typically returns

    a list (stack), and pushes the literal on to it.  e.g. 2

    takes the state and returns a function which, when evaluated,

    evaluates the state passed to 2 and pushes 2 onto it.

    i've implemented, just for demo purposes, dup swap pop i dip

    and all the k primitives.

    example:

          e(2;3;4;(+;*);`i)

       ,14

    which in joy is

          2 3 4 [+ *] i

    e should produce, modulo differences in the primitives, the same

    result as joy.  e takes the result of evaluation, which is a

    function, and executes it.  the inner function, which produces

    the functional input to e is more basic.  with some format-sugar

    to make it more readable (the actual object is rather ugly), we

    have:

          o a(2;3;4;(+;*);`i)

        i[[[[[;2];3];4];(+;*)]]

    [;2] composes 2 with the identity function, which is composed

    with 3, which is composed with 4, which is composed with the

    quotation (+;*), which is composed with i.

    the a function takes no time, and can't fail.  it just builds

    the composition.

    when the resulting composition is executed, the result is ,14.

## Narcoleptic Electron — 2005-08-19 18:13:02

    On 8/17/05, sa@... <sa@...> wrote:

     > in the languages we've been discussing, everything is a unary

    > function: stack -> stack.  in what i'm calling 'x', everything

    > is a unary function: function -> function.

    >

    > the initial state is the identity function.

    >

    > a literal is a function which takes the state and produces

    > a new function.  that function, when evaluated, evaluates

    > the state it took as an argument, which typically returns

    > a list (stack), and pushes the literal on to it.  e.g. 2

    > takes the state and returns a function which, when evaluated,

    > evaluates the state passed to 2 and pushes 2 onto it.

     What is the exact definition of "state" here?

     > i've implemented, just for demo purposes, dup swap pop i dip

    > and all the k primitives.

    >

    > example:

    >

    >       e(2;3;4;(+;*);`i)

    >    ,14

    >

    > which in joy is

    >

    >       2 3 4 [+ *] i

    >

    > e should produce, modulo differences in the primitives, the same

    > result as joy.  e takes the result of evaluation, which is a

    > function, and executes it.  the inner function, which produces

    > the functional input to e is more basic.  with some format-sugar

    > to make it more readable (the actual object is rather ugly), we

    > have:

    >

    >       o a(2;3;4;(+;*);`i)

    >     i[[[[[;2];3];4];(+;*)]]

    >

    > [;2] composes 2 with the identity function, which is composed

    > with 3, which is composed with 4, which is composed with the

    > quotation (+;*), which is composed with i.

    >

    > the a function takes no time, and can't fail.  it just builds

    > the composition.

    >

    > when the resulting composition is executed, the result is ,14.

     I don't understand.  It seems to me that this function->function

    paradigm applies to Joy as well: the stack that it receives as input

    can be considered a composition of the functions that produced that

    stack, and the function that is returned is the input function

    composed with the new function.

    For example:

    2 3 +

    results in the following:

    - Compose the identity function with the "2" function.

    - Compose the "identity o 2" function with the "3" function.

    - Compose the "identity o 2 o 3" function with the "+" function.

    - Execute the resulting function.

## Narcoleptic Electron — 2005-08-19 18:29:35

    More clarification on my question...

     On 8/19/05, Narcoleptic Electron <narcoleptic.electron@...> wrote:

    > On 8/17/05, sa@... <sa@...> wrote:

    > > in the languages we've been discussing, everything is a unary

    > > function: stack -> stack.  in what i'm calling 'x', everything

    > > is a unary function: function -> function.

    > >

    > > the initial state is the identity function.

    > >

    > > a literal is a function which takes the state and produces

    > > a new function.  that function, when evaluated, evaluates

    > > the state it took as an argument, which typically returns

    > > a list (stack), and pushes the literal on to it.  e.g. 2

    > > takes the state and returns a function which, when evaluated,

    > > evaluates the state passed to 2 and pushes 2 onto it.

    >

    > What is the exact definition of "state" here?

    >

    > > i've implemented, just for demo purposes, dup swap pop i dip

    > > and all the k primitives.

    > >

    > > example:

    > >

    > >       e(2;3;4;(+;*);`i)

    > >    ,14

    > >

    > > which in joy is

    > >

    > >       2 3 4 [+ *] i

    > >

    > > e should produce, modulo differences in the primitives, the same

    > > result as joy.  e takes the result of evaluation, which is a

    > > function, and executes it.  the inner function, which produces

    > > the functional input to e is more basic.  with some format-sugar

    > > to make it more readable (the actual object is rather ugly), we

    > > have:

    > >

    > >       o a(2;3;4;(+;*);`i)

    > >     i[[[[[;2];3];4];(+;*)]]

    > >

    > > [;2] composes 2 with the identity function, which is composed

    > > with 3, which is composed with 4, which is composed with the

    > > quotation (+;*), which is composed with i.

    > >

    > > the a function takes no time, and can't fail.  it just builds

    > > the composition.

    > >

    > > when the resulting composition is executed, the result is ,14.

    >

    > I don't understand.  It seems to me that this function->function

    > paradigm applies to Joy as well: the stack that it receives as input

    > can be considered a composition of the functions that produced that

    > stack, and the function that is returned is the input function

    > composed with the new function.

    >

    > For example:

    >

    > 2 3 +

    >

    > results in the following:

    > - Compose the identity function with the "2" function.

    > - Compose the "identity o 2" function with the "3" function.

    > - Compose the "identity o 2 o 3" function with the "+" function.

    > - Execute the resulting function.

    I wasn't very clear here.

    Here is my understanding of applying the function->function idea to

    the Joy code "2 3 +":

    - Function "2" takes the stack as input and returns the stack with 2

    pushed onto it.

    - Function "3" takes the stack as input and returns the stack with 3

    pushed onto it.

    When executed after function "2", you get the initial stack with 2 and

    3 pushed onto it.

    When composed with function "2", you get a function that produces the

    initial stack with 2 and 3 pushed onto it.

    - Function "+" returns the stack with the top two items popped, and

    the sum pushed.

    When executed after function "2 o 3", you get the initial stack with 5

    pushed onto it.

    When composed with function "2 o 3", you get a function that produces

    the initial stack with 5 pushed onto it.

    The resulting composed function is "2 o 3 o +", which when executed,

    takes a stack and pushes 5 onto it.

    Is this not the same thing as your language?

## stevan apter — 2005-08-19 21:43:03

    ----- Original Message -----

    From: "Narcoleptic Electron" <narcoleptic.electron@...>

    To: <concatenative@yahoogroups.com>

    Sent: Friday, August 19, 2005 2:29 PM

    Subject: Re: [stack] type-lifted joy

    More clarification on my question...

    On 8/19/05, Narcoleptic Electron <narcoleptic.electron@...> wrote:

    > On 8/17/05, sa@... <sa@...> wrote:

    > > in the languages we've been discussing, everything is a unary

    > > function: stack -> stack.  in what i'm calling 'x', everything

    > > is a unary function: function -> function.

    > >

    > > the initial state is the identity function.

    > >

    > > a literal is a function which takes the state and produces

    > > a new function.  that function, when evaluated, evaluates

    > > the state it took as an argument, which typically returns

    > > a list (stack), and pushes the literal on to it.  e.g. 2

    > > takes the state and returns a function which, when evaluated,

    > > evaluates the state passed to 2 and pushes 2 onto it.

    >

    > What is the exact definition of "state" here?

    >

    > > i've implemented, just for demo purposes, dup swap pop i dip

    > > and all the k primitives.

    > >

    > > example:

    > >

    > >       e(2;3;4;(+;*);`i)

    > >    ,14

    > >

    > > which in joy is

    > >

    > >       2 3 4 [+ *] i

    > >

    > > e should produce, modulo differences in the primitives, the same

    > > result as joy.  e takes the result of evaluation, which is a

    > > function, and executes it.  the inner function, which produces

    > > the functional input to e is more basic.  with some format-sugar

    > > to make it more readable (the actual object is rather ugly), we

    > > have:

    > >

    > >       o a(2;3;4;(+;*);`i)

    > >     i[[[[[;2];3];4];(+;*)]]

    > >

    > > [;2] composes 2 with the identity function, which is composed

    > > with 3, which is composed with 4, which is composed with the

    > > quotation (+;*), which is composed with i.

    > >

    > > the a function takes no time, and can't fail.  it just builds

    > > the composition.

    > >

    > > when the resulting composition is executed, the result is ,14.

    >

    > I don't understand.  It seems to me that this function->function

    > paradigm applies to Joy as well: the stack that it receives as input

    > can be considered a composition of the functions that produced that

    > stack, and the function that is returned is the input function

    > composed with the new function.

    >

    > For example:

    >

    > 2 3 +

    >

    > results in the following:

    > - Compose the identity function with the "2" function.

    > - Compose the "identity o 2" function with the "3" function.

    > - Compose the "identity o 2 o 3" function with the "+" function.

    > - Execute the resulting function.

    I wasn't very clear here.

    Here is my understanding of applying the function->function idea to

    the Joy code "2 3 +":

    - Function "2" takes the stack as input and returns the stack with 2

    pushed onto it.

        there's is no stack.  2 takes the identity function and returns

        a function which, when evaluated, appends 2 to the empty list.

        write that function as [;2] (just to give it a name).

    - Function "3" takes the stack as input and returns the stack with 3

    pushed onto it.

        3 takes [;2] and returns a function which, when evaluated, appends 3

        to the result of evaluating [;2].  write that function as [[;2];3].

    When executed after function "2", you get the initial stack with 2 and

    3 pushed onto it.

    When composed with function "2", you get a function that produces the

    initial stack with 2 and 3 pushed onto it.

    - Function "+" returns the stack with the top two items popped, and

    the sum pushed.

        + takes [[;2];3] and returns a function which, when evaluated, takes

        the last two elements of the list-result of evaluating [[;2];3], adds

        them, and appends the result to the list you get from dropping the

        last two elements.  write that function as +[[;2];3].

    When executed after function "2 o 3", you get the initial stack with 5

    pushed onto it.

    When composed with function "2 o 3", you get a function that produces

    the initial stack with 5 pushed onto it.

    The resulting composed function is "2 o 3 o +", which when executed,

    takes a stack and pushes 5 onto it.

    Is this not the same thing as your language?

        i suppose you could think of x as compiling the input program

        to a function which, when evaluated, returns what joy would

        return when evaluating the same input program.  joy and x are

        extensionally equivalent.  x just breaks evaluation into two

        parts:  construction of a function, and then evaluation of

        that function.  i haven't really had time to explore the

        implications of this approach.  it may come to nothing.

    Yahoo! Groups Links