Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

Is this use of DOES> according to the standard - and portable?

110 views
Skip to first unread message

Hans Bezemer

unread,
Nov 28, 2011, 6:18:52 PM11/28/11
to
6.1.1250 DOES>
"Replace the execution semantics of the most recent definition,
referred to as name, with the name execution semantics given below. An
ambiguous condition exists if name was not defined with CREATE or a
user-defined word that calls CREATE."

So this is valid AND portable:

Type `bye' to exit
: array create cells allot ; ok
16 array myarray ok
myarray . -1213636248 ok
does> swap cells + ; ok
0 myarray . -1213636248 ok
1 myarray . -1213636244 ok
16 0 myarray ! ok
32 1 myarray ! ok
0 myarray ? 16 ok
1 myarray ? 32 ok

Or is it?

Hans Bezemer

Alex McDonald

unread,
Nov 28, 2011, 6:44:47 PM11/28/11
to
It certainly works as advertised here on my system; and I believe it's
valid given the spec.

Krishna Myneni

unread,
Nov 28, 2011, 7:16:22 PM11/28/11
to
Doesn't work in kForth:
--
kForth v 1.5.3 (Build: 2011-11-02)
Copyright (c) 1998--2011 Krishna Myneni
Contributions by: dpw gd mu bk abs tn cmb bg dnw
Provided under the GNU General Public License.

ok
: array create cells allot ;
ok
16 array myarray
ok
myarray .
140114648 ok
does> swap cells + ;
Line 4: Compiler Error(2): End of definition with no beginning
does> swap cells + ;
--

Krishna

Doug Hoffman

unread,
Nov 28, 2011, 8:30:10 PM11/28/11
to
On 11/28/11 6:18 PM, Hans Bezemer wrote:
> 6.1.1250 DOES>
> "Replace the execution semantics of the most recent definition,
> referred to as name, with the name execution semantics given below. An
> ambiguous condition exists if name was not defined with CREATE or a
> user-defined word that calls CREATE."

You left out:

6.1.1250 DOES>
Interpretation: Interpretation semantics for this word are undefined.

> So this is valid AND portable:

Since you are using DOES> in an undefined manner it doesn't seem likely
that it's portable.

FWIW, Carbon MacForth will only accept DOES> during compilation (i.e.,
your code snippet didn't work).

-Doug

Krishna Myneni

unread,
Nov 28, 2011, 9:20:16 PM11/28/11
to
On Nov 28, 5:18 pm, Hans Bezemer <theb...@xs4all.nl> wrote:
I believe the following should be standard, and portable:

--
: todo1 does> swap cells + ;
: array create cells allot ;
--

Then,

16 array myarray
myarray .
todo1 \ <-- gives myarray its execution behavior
\ etc.

So, if you're looking to assign execution behavior to a word after it
has been created with a defining word, and choose among a list of
behaviors, you should be able to do:

--
: todo1 does> ... ;
: todo2 does> ... ;
\etc.

: array create ... ;

<n> array myarray
todo<m> \ choose among several execution behaviors
--

Krishna


Bee

unread,
Nov 28, 2011, 10:18:44 PM11/28/11
to
No that is not portable.
But should be is:

: .rno ( -- ) \ Radix Number Output
DOES> C@ BASE @ >R BASE ! U. R> BASE ! ;

CREATE .B ( n -- ) 2 C, .rno
CREATE .O ( n -- ) 8 C, .rno
CREATE .D ( n -- ) 10 C, .rno
CREATE .H ( n -- ) 16 C, .rno

-Bill

A. K.

unread,
Nov 29, 2011, 12:49:22 AM11/29/11
to
On 29.11.2011 04:18, Bee wrote:
> But should be is:
>
> : .rno ( -- ) \ Radix Number Output
> DOES> C@ BASE @>R BASE ! U. R> BASE ! ;

You are making a silent assumption here that DOES> works without CREATE:

6.1.1250 DOES>
does CORE
...

Ed

unread,
Nov 29, 2011, 2:29:03 AM11/29/11
to
Hans Bezemer wrote:
> 6.1.1250 DOES>
> "Replace the execution semantics of the most recent definition,
> referred to as name, with the name execution semantics given below. An
> ambiguous condition exists if name was not defined with CREATE or a
> user-defined word that calls CREATE."
>
> So this is valid AND portable:
> ...

IMO if it looks wrong i.e. it doesn't conform to any known "common
practice" then it should not be counted on - regardless of what the
wording of the Standard might be interpreted to allow.

Standards seek to define common practice - not quirky practice.
Unless stated otherwise it's reasonable to assume the TC's
wording was limited to reflecting existing/traditional practice.

Is there ever a case for interpreting the Standard in a way the
authors had likely *not* intended? I can think of two instances.

1) the TC was dealing with new/unproven concepts and bungled it
2) the definition can be interpreted in a way that adds facility while
maintaining traditional practice

Would your examples fit the latter?



Hans Bezemer

unread,
Nov 29, 2011, 3:03:48 AM11/29/11
to
Alex McDonald wrote:

> It certainly works as advertised here on my system; and I believe it's
> valid given the spec.

True, I didn't see that interpretation isn't defined. But I think it's cool
to append execution semantics immediately after defining a CREATE without a
previous definition. The behavior shown is due to the definition in gForth:

see does>
noname :
dodoes, here !does ] defstart :-hook ;
latestxt

noname :
;-hook ?struc exit-like (compile) (does>) dodoes, defstart :-hook ;
latestxt
interpret/compile DOES> immediate ok

You'll see that it kicks the compiler into compilation mode when
interpreting.

Hans Bezemer

Elizabeth D. Rather

unread,
Nov 29, 2011, 3:09:37 AM11/29/11
to
There are several issues here, some of which have been pointed out, but
to clarify:

1. The thing being modified must have been defined by CREATE (because
not all defining words leave an appropriately modifiable structure).

2. DOES> "has no interpretation semantics" means the usage above isn't
appropriate. It is intended to be the second part of a two-part colon
definition.

The fact that this appears to have worked above means that this
particular implementation leaves a CREATEd word structured in such a way
that new semantics can be attached to it. But DOES> is intended to
create a new *defining word* that can be used to create new definitions
of the same class. The above usage managed to modify the definition
myarray, but that is a single definition that cannot be used to make new
definitions with that behavior. It did not make array into a new
defining word with the desired indexing behavior, so even though it
appeared to do something appropriate with myarray, it didn't fulfill the
purpose for which DOES> exists.

And, most assuredly, other systems will not allow this to work. So, the
fact that DOES> was used interpretively means it is both non-standard
and non-portable.

Cheers,
Elizabeth

--
==================================================
Elizabeth D. Rather (US & Canada) 800-55-FORTH
FORTH Inc. +1 310.999.6784
5959 West Century Blvd. Suite 700
Los Angeles, CA 90045
http://www.forth.com

"Forth-based products and Services for real-time
applications since 1973."
==================================================

Bernd Paysan

unread,
Nov 29, 2011, 4:01:12 AM11/29/11
to
Hans Bezemer wrote:

> Alex McDonald wrote:
>
>> It certainly works as advertised here on my system; and I believe
>> it's valid given the spec.
>
> True, I didn't see that interpretation isn't defined. But I think it's
> cool to append execution semantics immediately after defining a CREATE
> without a previous definition. The behavior shown is due to the
> definition in gForth:

Yes, Gforth allows this. I implemented this due to the "no arbitrary
limits" policy of GNU language ports. It is fairly obvious what a DOES>
in interpretation mode should do.

--
Bernd Paysan
"If you want it done right, you have to do it yourself"
http://bernd-paysan.de/

Anton Ertl

unread,
Nov 29, 2011, 6:19:04 AM11/29/11
to
Hans Bezemer <the...@xs4all.nl> writes:
>6.1.1250 DOES>
>"Replace the execution semantics of the most recent definition,
>referred to as name, with the name execution semantics given below. An
>ambiguous condition exists if name was not defined with CREATE or a
>user-defined word that calls CREATE."
>
>So this is valid AND portable:
>
>Type `bye' to exit
>: array create cells allot ; ok
>16 array myarray ok
>myarray . -1213636248 ok
>does> swap cells + ; ok

This is non-standard because the standard does not define
interpretation semantics for DOES>. And, as other posters wrote, it
also does not work on some standard systems, so it is not portable.

- anton
--
M. Anton Ertl http://www.complang.tuwien.ac.at/anton/home.html
comp.lang.forth FAQs: http://www.complang.tuwien.ac.at/forth/faq/toc.html
New standard: http://www.forth200x.org/forth200x.html
EuroForth 2011: http://www.euroforth.org/ef11/

Alex McDonald

unread,
Nov 29, 2011, 6:38:40 AM11/29/11
to
You missed what followed?

CREATE .B ( n -- ) 2 C, .rno
^^^^^^

Alex McDonald

unread,
Nov 29, 2011, 6:59:19 AM11/29/11
to
My Forth simply generates a :NONAME definition that modifies the
action of CREATE. This;

: x create .a. does> .b. ;

is compiled in two parts as

: x create .a. ;
:noname [ modify X for "DOES>"-like behaviour with this XT ] .b. ;

Given that

: x create .a. does> .b. does> .c. ;

is ANS valid, then I would assume that any implementation that doesn't
allow DOES> in interpreted state should be trivially modifiable to do
so.

Alex McDonald

unread,
Nov 29, 2011, 7:10:47 AM11/29/11
to
The limitation seems to be imposed by colon-sys. If (as is the case in
my Forth and a number of others) the colon-sys is null from : then the
limitation doesn't apply.

>
> The fact that this appears to have worked above means that this
> particular implementation leaves a CREATEd word structured in such a way
> that new semantics can be attached to it.

That must always be the case, otherwise DOES>, interpreted or
compiled, wouldn't work as CREATE is not immediate. It's the colon-sys
that interferes with an interpreted version.

> But DOES> is intended to
> create a new *defining word* that can be used to create new definitions
> of the same class.  The above usage managed to modify the definition
> myarray, but that is a single definition that cannot be used to make new
> definitions with that behavior.

But effectively in this case the interpretive DOES> is simply the
definition of an object, rather than a class. It seems a perfectly
reasonable approach, since not all classes demand more than one object
stamped from them.

> It did not make array into a new
> defining word with the desired indexing behavior, so even though it
> appeared to do something appropriate with myarray, it didn't fulfill the
> purpose for which DOES> exists.

The spec doesn't talk of a purpose for DOES>, and only of typical use
in the appendix; although that may have been the TC's intent.

>
> And, most assuredly, other systems will not allow this to work. So, the
> fact that DOES> was used interpretively means it is both non-standard
> and non-portable.

True.

>
> Cheers,
> Elizabeth
>
> --
> ==================================================
> Elizabeth D. Rather   (US & Canada)   800-55-FORTH
> FORTH Inc.                         +1 310.999.6784
> 5959 West Century Blvd. Suite 700
> Los Angeles, CA 90045http://www.forth.com

Andrew Haley

unread,
Nov 29, 2011, 9:20:49 AM11/29/11
to
Alex McDonald <bl...@rivadpm.com> wrote:
> On Nov 29, 8:09?am, "Elizabeth D. Rather" <erat...@forth.com> wrote:
>> On 11/28/11 1:18 PM, Hans Bezemer wrote:
>>
>> > 6.1.1250 DOES>
>> > "Replace the execution semantics of the most recent definition,
>> > referred to as name, with the name execution semantics given below. An
>> > ambiguous condition exists if name was not defined with CREATE or a
>> > user-defined word that calls CREATE."
>>
>> > So this is valid AND portable:
>>
>> > Type `bye' to exit
>> > : array create cells allot ; ?ok
>> > 16 array myarray ?ok
>> > myarray . -1213636248 ?ok
>> > does> ?swap cells + ; ?ok
>> > 0 myarray . -1213636248 ?ok
>> > 1 myarray . -1213636244 ?ok
>> > 16 0 myarray ! ?ok
>> > 32 1 myarray ! ?ok
>> > 0 myarray ? 16 ?ok
>> > 1 myarray ? 32 ?ok
>>
>> > Or is it?
>>
>> > Hans Bezemer
>>
>> There are several issues here, some of which have been pointed out, but
>> to clarify:
>>
>> 1. The thing being modified must have been defined by CREATE (because
>> not all defining words leave an appropriately modifiable structure).
>>
>> 2. DOES> "has no interpretation semantics" means the usage above isn't
>> appropriate. It is intended to be the second part of a two-part colon
>> definition.
>
> The limitation seems to be imposed by colon-sys. If (as is the case in
> my Forth and a number of others) the colon-sys is null from : then the
> limitation doesn't apply.

Not necessarily. DOES> might not be a word that sets compilation
state, for example.

Andrew.

Alex McDonald

unread,
Nov 29, 2011, 9:38:54 AM11/29/11
to
On Nov 29, 2:20 pm, Andrew Haley <andre...@littlepinkcloud.invalid>
wrote:
: does> postpone ] postpone does> ; immediate

Would that suffice?

Andrew Haley

unread,
Nov 29, 2011, 10:47:33 AM11/29/11
to
Alex McDonald <bl...@rivadpm.com> wrote:
> On Nov 29, 2:20?pm, Andrew Haley <andre...@littlepinkcloud.invalid>
>> Not necessarily. ?DOES> might not be a word that sets compilation
>> state, for example.
>
> : does> postpone ] postpone does> ; immediate
>
> Would that suffice?

It might well, yes.

Andrew.

Hans Bezemer

unread,
Nov 29, 2011, 12:42:41 PM11/29/11
to
Alex McDonald wrote:
>> The fact that this appears to have worked above means that this
>> particular implementation leaves a CREATEd word structured in such a way
>> that new semantics can be attached to it.
>
> That must always be the case, otherwise DOES>, interpreted or
> compiled, wouldn't work as CREATE is not immediate. It's the colon-sys
> that interferes with an interpreted version.
I came to exactly the same conclusion after reading the standard: There is
NOTHING between CREATE and DOES> and I certainly may assume DOES> isn't
immediate either. So CREATE must be left in such a state that a DOES> can
always add additional behavior, since there is nothing that "closes" a
CREATE unless the DOES> itself.

>>But DOES> is intended to
>> create a new *defining word* that can be used to create new definitions
>> of the same class.  The above usage managed to modify the definition
>> myarray, but that is a single definition that cannot be used to make new
>> definitions with that behavior.
>
> But effectively in this case the interpretive DOES> is simply the
> definition of an object, rather than a class. It seems a perfectly
> reasonable approach, since not all classes demand more than one object
> stamped from them.
Same to me: that's why I thought this "addition" is useful. Take a quick
table that gets his runtime behavior appended without an obligatory
definition that clouds and clutters the source, e.g.

: .range2 0 .r ." -" 0 .r ; \ difference two or more
: .range1 0 .r ." , " 0 .r ; \ difference one
: .range0 drop 0 .r ; \ no difference
\ select printing routine
create .range ' .range0 , ' .range1 , ' .range2 ,
does> >r over over - 2 min cells r> + @ execute ;

Hans Bezemer

Ed

unread,
Nov 29, 2011, 6:36:26 PM11/29/11
to
Perhaps so but is there a classic/conventional forth where it wouldn't work?

The question for me would be whether or not this factoring had advantages
over usual methods (?)





Ed

unread,
Nov 29, 2011, 6:36:55 PM11/29/11
to
Bee wrote:
> ...
> No that is not portable.
> But should be is:
>
> : .rno ( -- ) \ Radix Number Output
> DOES> C@ BASE @ >R BASE ! U. R> BASE ! ;
>
> CREATE .B ( n -- ) 2 C, .rno
> CREATE .O ( n -- ) 8 C, .rno
> CREATE .D ( n -- ) 10 C, .rno
> CREATE .H ( n -- ) 16 C, .rno

Interesting factoring!

For reasons peculiar to my forth I've added an alternative to
CREATE DOES> called BUILD which works as follows:

: CONSTANT ['] @ BUILD , ;

23 CONSTANT test ok
test . 23 ok

Applying your factoring technique to BUILD we get:

:noname ( adr -- ) \ Radix Number Output
c@ base @ >r base ! u. r> base ! ; ok

( xt)
dup build .B 2 c, ok
dup build .O 8 c, ok
dup build .D 10 c, ok
build .H 16 c, ok

23 .b 10111 ok
23 .o 27 ok
23 .h 17 ok

I always thought BUILD required named words for the run-time part.
Your example has shown me how to use unnamed words with BUILD.
Thanks!





Ed

unread,
Nov 29, 2011, 7:14:07 PM11/29/11
to
.RNO didn't CREATE the current definition so all bets are off.

6.1.1250 DOES>
...
Compilation: ( C: colon-sys1 -- colon-sys2 )

Append the run-time semantics below to the current definition. ...



Hans Bezemer

unread,
Nov 30, 2011, 3:10:39 AM11/30/11
to
Ed wrote:
> .RNO didn't CREATE the current definition so all bets are off.
>
> 6.1.1250 DOES>
> ...
> Compilation: ( C: colon-sys1 -- colon-sys2 )
>
> Append the run-time semantics below to the current definition. ...
Depends on that you define as "current definition". If this is the same
as "most recent definition" then I don't see any problems. The TC doesn't
go any further than "typical use" - it doesn't elaborate and did away with
SMUDGE. So how many options do implementors have?

Hans Bezemer

Gerry Jackson

unread,
Nov 30, 2011, 3:40:21 AM11/30/11
to
On 29/11/2011 17:42, Hans Bezemer wrote:

>> But effectively in this case the interpretive DOES> is simply the
>> definition of an object, rather than a class. It seems a perfectly
>> reasonable approach, since not all classes demand more than one object
>> stamped from them.
> Same to me: that's why I thought this "addition" is useful. Take a quick
> table that gets his runtime behavior appended without an obligatory
> definition that clouds and clutters the source, e.g.
>
> : .range2 0 .r ." -" 0 .r ; \ difference two or more
> : .range1 0 .r ." , " 0 .r ; \ difference one
> : .range0 drop 0 .r ; \ no difference
> \ select printing routine
> create .range ' .range0 , ' .range1 , ' .range2 ,
> does> >r over over - 2 min cells r> + @ execute ;
>
> Hans Bezemer
>

An alternative that is standard and also doesn't have an "obligatory
definition that clouds and clutters the source" builds on Andrew Haley's
idea from another discussion:

: pass >r ' execute r> ; immediate
here ' .range0 , ' .range1 , ' .range2 ,
pass : .range 2dup - 2 min cells literal + @ execute ;

with slightly simpler code in .range. But it has the disadvantage of
needing the word PASS. Of course if your Forth has a "ruthless approach
to simplification" - a RATS Forth? :-) - see
https://groups.google.com/group/comp.lang.forth/browse_frm/thread/8cf39367b62d945d/7c6d3afea8835b68?hl=en#7c6d3afea8835b68
you don't even need PASS.

--
Gerry

Alex McDonald

unread,
Nov 30, 2011, 4:24:16 AM11/30/11
to
DOES> doesn't know what word contains the CREATE; how would it know
and why would it care? The definition DOES> is modifying has to, in
the words of the spec, be some word that is defined by CREATE and
that's not necessarily true of .RNO.

Andrew Haley

unread,
Nov 30, 2011, 6:28:22 AM11/30/11
to
It's dawned on me that this is wrong. In the above example DOES> is
postponed, but when used in interpretation mode because it's not a
part of any definition there's no way to execute it.

So, this is wrong:

create counter 0 , does> 1 over +! @ ;

But this works, and is standard:

:noname create 0 , does> 1 over +! @ ; execute counter

As is this:

:noname does> 1 over +! @ ;
create counter 0 , execute

So I don't think there's any practical need for DOES> in
interpretation state.

Andrew.

JennyB

unread,
Nov 30, 2011, 9:19:40 AM11/30/11
to han...@xs4all.nl
The "current definition" in this case is ".RNO". It has to be. This happens when DOES> is compiled, so any child words that the definition creates when it is executed do not yet exist. The run-time semantics appended by DOES> can be compared to IMMEDIATE - both modify the most recent definition. I don't see any reason not to use the same mechanism to find the most recent definition in each case, though it doesn't make much sense for DOES> to modify anything that has not been defined by CREATE.

I suppose it is just possible that a DOES> which assumes that a CREATE has been previously compile in the current definition could work by modifying that code at compile time, but I don't see how or why that might be done.

In any case, the fact that : CREATE ... DOES> ... DOES> ... : is Standard shows that : ... DOES> ... ; must also be.

BruceMcF

unread,
Nov 30, 2011, 11:11:40 AM11/30/11
to
On Nov 30, 9:19 am, JennyB <jennybr...@googlemail.com> wrote:
> The run-time semantics appended by DOES> can be compared to IMMEDIATE
> - both modify the most recent definition. I don't see any reason
> not to use the same mechanism to find the most recent definition
> in each case, though it doesn't make much sense for DOES> to modify
> anything that has not been defined by CREATE.

This is, indeed, something to keep in mind for people writing code
that they intend to port ~ your system may not use CREATE as a factor
of words like : or CONSTANT or VARIABLE but another system certainly
may, so when CREATE and the DOES> are in different words, the word
containing DOES> has to be used *like* IMMEDIATE, with no other
defining words in between.

However, if Ed is saying that CREATE and DOES> have to be in the same
word, that simply disagrees with the explicit specification of DOES> ~
its absurd to suggest that the "current definition" in a section on
compilation semantics is anything other than the word currently being
compiled that contains DOES> and its absurd to suggest that "the most
recent definition" in a section on the execution semantics is anything
but the definition most recently compiled into the dictionary by a
CREATE, at the time that the behavior compiled by DOES> executes ...
given that "definition" is defined as:

"definition:
A Forth execution procedure compiled into the dictionary."

An implementation that imposed that constraint would be a non-standard
implementation.

Hans Bezemer

unread,
Nov 30, 2011, 11:55:09 AM11/30/11
to
Gerry Jackson wrote:
>> : .range2 0 .r ." -" 0 .r ; \ difference two or more
>> : .range1 0 .r ." , " 0 .r ; \ difference one
>> : .range0 drop 0 .r ; \ no difference
>> \ select printing routine
>> create .range ' .range0 , ' .range1 , ' .range2 ,
>> does> >r over over - 2 min cells r> + @ execute ;
>>
>> Hans Bezemer
>>
>
> An alternative that is standard and also doesn't have an "obligatory
> definition that clouds and clutters the source" builds on Andrew Haley's
> idea from another discussion:
>
> : pass >r ' execute r> ; immediate
> here ' .range0 , ' .range1 , ' .range2 ,
> pass : .range 2dup - 2 min cells literal + @ execute ;
>
> with slightly simpler code in .range. But it has the disadvantage of
> needing the word PASS. Of course if your Forth has a "ruthless approach
> to simplification" - a RATS Forth? :-)

Well, I particularly don't like HERE in user programs. When used in compiler
words, ok, but not in my main program if I can avoid it.

The point is that in my version it is completely clear what I'm doing: I'm
defining a named array of pointers constants to words that gets a special
runtime appended. When I append an additional stack comment it is
completely clear what it does.

In your version the connection between this unnamed pointer array and the
following definition is unclear. PASS is non-standard, I don't know what it
does. The whole thing is quite fuzzy IMHO. Again IMHO, this kind of coding
is what gives Forth a bad name, a "write only" language.

As Paysan correctly stated, there is no doubt what an interpreted DOES>
should do - and he proved it by doing it. Others, included myself of
course, have shown that it is not merely a quirk but it can be used in real
life programs with added benefits.

But I think the difference between our coding styles shows by using 2DUP. In
some systems that may be a primitive with added (though small) performance
benefits. In others it is simply : 2DUP OVER OVER ; with speed penalties. I
use 2DUP only when there is either a double number OR an address/count pair
to be handled - even when that means a speed penalty, simply because I want
to express that I'm handling two associated items. If not, I use OVER OVER
just to signal these are two UNassociated items.

Again, I've had lots of trouble when I was modifying a program where a COUNT
was used where I'd expect a C@+, simply because I was breaking my head
where that string came from. Plus points if you use it in a word where
string IS used somewhere for added confusion.

Low bugcounts and palletable modification times are closely associated with
clear coding. Obfuscated programming is an art in itself, but not very
valuable IRL.

Hans Bezemer


BruceMcF

unread,
Nov 30, 2011, 2:09:18 PM11/30/11
to
On Nov 30, 3:40 am, Gerry Jackson <ge...@jackson9000.fsnet.co.uk>
wrote:
> An alternative that is standard and also doesn't have an "obligatory
> definition that clouds and clutters the source" builds on Andrew
> Haley's idea from another discussion:

> : pass >r ' execute r> ; immediate
> here ' .range0 , ' .range1 , ' .range2 ,
> pass : .range  2dup - 2 min cells literal + @ execute ;

> with slightly simpler code in .range. But it has the disadvantage of
> needing the word PASS. Of course if your Forth has a "ruthless approach
> to simplification" - a RATS Forth? :-) - seehttps://groups.google.com/group/comp.lang.forth/browse_frm/thread/8cf...
> you don't even need PASS.

Wouldn't:

: .range2 0 .R ." -" 0 .R ; \ difference two or more
: .range1 0 .R ." , " 0 .R ; \ difference one
: .range0 DROP 0 .R ; \ no difference
\ select printing routine

:NONAME DOES> >R OVER OVER - 2 MIN CELLS R> + @ EXECUTE ;
CREATE .range ' .range0 , ' .range1 , ' .range2 ,
EXECUTE

... have the same effect?

Ed

unread,
Dec 1, 2011, 2:25:23 AM12/1/11
to
> ...

The purpose of DOES> in forth is to allow creation of defining words.
Definers consist of two parts - a compile-time part and run-time part,
in the form:

A.6.1.1250 DOES>

Typical use: : X ... DOES> ... ;

DOES> terminates the compile-time part of the current definition
(the definer) and appends the subsequent run-time semantics to
the child CREATEd by the compile-time part.

Since .RNO doesn't have a compile-time part it's not a defining
word. Not being a definer, using DOES> was illegal (IMO).

That Bill's use of DOES> worked and did what he wanted is cute
but immaterial. If it doesn't provide anything beyond what a defining
word would do (does it?) then there is no reason to use it, or for a
Standard to support it.



Gerry Jackson

unread,
Dec 1, 2011, 3:51:22 AM12/1/11
to
Yes, you're right, much simpler

--
Gerry

Gerry Jackson

unread,
Dec 1, 2011, 4:19:37 AM12/1/11
to
On 30/11/2011 16:55, Hans Bezemer wrote:
> Gerry Jackson wrote:
>>> : .range2 0 .r ." -" 0 .r ; \ difference two or more
>>> : .range1 0 .r ." , " 0 .r ; \ difference one
>>> : .range0 drop 0 .r ; \ no difference
>>> \ select printing routine
>>> create .range ' .range0 , ' .range1 , ' .range2 ,
>>> does> >r over over - 2 min cells r> + @ execute ;
>>>
>>> Hans Bezemer
>>>
>>
>> An alternative that is standard and also doesn't have an "obligatory
>> definition that clouds and clutters the source" builds on Andrew Haley's
>> idea from another discussion:
>>
>> : pass >r ' execute r> ; immediate
>> here ' .range0 , ' .range1 , ' .range2 ,
>> pass : .range 2dup - 2 min cells literal + @ execute ;
>>
>> with slightly simpler code in .range. But it has the disadvantage of
>> needing the word PASS. Of course if your Forth has a "ruthless approach
>> to simplification" - a RATS Forth? :-)
>
> Well, I particularly don't like HERE in user programs. When used in compiler
> words, ok, but not in my main program if I can avoid it.

That seems strange to me, but each to his own.

>
> The point is that in my version it is completely clear what I'm doing: I'm
> defining a named array of pointers constants to words that gets a special
> runtime appended. When I append an additional stack comment it is
> completely clear what it does.

Or rather what it would do on some Forths if they accepted it. Clarity
is largely a matter of opinion and familiarity with a language and its
idioms as well as layout. After all a line like
create .range ' .range0 , ' .range1 , ' .range2 ,
is incomprehensible to most of the world's programmers. I find my
version just as clear. Use of unfamiliar non-standard words, like C@+
which you seem to favour below, do not lead to clarity.

>
> In your version the connection between this unnamed pointer array and the
> following definition is unclear. PASS is non-standard,

On the contrary it *is* standard ANS Forth, unlike your code.

> I don't know what it does.

Too lazy to work it out? It's simple enough.

> The whole thing is quite fuzzy IMHO. Again IMHO, this kind of coding
> is what gives Forth a bad name, a "write only" language.

IMHO ???

>
> As Paysan correctly stated, there is no doubt what an interpreted DOES>
> should do - and he proved it by doing it. Others, included myself of
> course, have shown that it is not merely a quirk but it can be used in real
> life programs with added benefits.

I don't disagree, but it is non-standard at present and therefore not
portable. That is fine if you're not interested in portability but
useless to those who are. If you feel that strongly about it raise an
RfD to get the standard changed.

>
> But I think the difference between our coding styles shows by using 2DUP. In
> some systems that may be a primitive with added (though small) performance
> benefits. In others it is simply : 2DUP OVER OVER ; with speed penalties. I
> use 2DUP only when there is either a double number OR an address/count pair
> to be handled - even when that means a speed penalty, simply because I want
> to express that I'm handling two associated items. If not, I use OVER OVER
> just to signal these are two UNassociated item

To me that is unnecessarily pedantic and rather silly.

>
> Again, I've had lots of trouble when I was modifying a program where a COUNT
> was used where I'd expect a C@+, simply because I was breaking my head
> where that string came from. Plus points if you use it in a word where
> string IS used somewhere for added confusion.

What has that got to do with this discussion? C@+ isn't a standard word,
why should someone use it just because you prefer it.

>
> Low bugcounts and palletable modification times are closely associated with
> clear coding. Obfuscated programming is an art in itself, but not very
> valuable IRL.

Hallelujah!

--
Gerry

Hans Bezemer

unread,
Dec 1, 2011, 8:28:36 AM12/1/11
to
Gerry Jackson wrote:

> On 30/11/2011 16:55, Hans Bezemer wrote:
>> Well, I particularly don't like HERE in user programs. When used in
>> compiler words, ok, but not in my main program if I can avoid it.
>
> That seems strange to me, but each to his own.
It is not that strange given that Chuck said one of the reasons that he
didn't like ANS Forth and particularly the CORE wordset was it carried too
many words that a "normal" applications programmer should never use (like
DOES>, HERE, etc). I tend to agree with him, so I try to hide all the dirty
internal bits in a layer that doesn't concern me when I'm getting down to
the problem. Even better, I tend not to use it at all if it doesn't help me
VERY much later on.

> Or rather what it would do on some Forths if they accepted it. Clarity
> is largely a matter of opinion and familiarity with a language and its
> idioms as well as layout. After all a line like
> create .range ' .range0 , ' .range1 , ' .range2 ,
> is incomprehensible to most of the world's programmers. I find my
> version just as clear. Use of unfamiliar non-standard words, like C@+
> which you seem to favour below, do not lead to clarity.
We're talking about two different things here. I'm talking of a syntax that
would IMHO better express what I'm trying to do than the standard way. I'm
assuming one can read Forth, but that was (I think) obvious straight on,
otherwise this discussion would be just as futile as when I was responding
in Dutch.


>> In your version the connection between this unnamed pointer array and the
>> following definition is unclear. PASS is non-standard,
> On the contrary it *is* standard ANS Forth, unlike your code.
Never saw it in the standard (leafing) Nope, it's not there.

> Too lazy to work it out? It's simple enough.
That's my point: if it's obvious I don't have to work it out. If it's not
obvious any kind of error is just around the corner.

> > The whole thing is quite fuzzy IMHO. Again IMHO, this kind of coding
>> is what gives Forth a bad name, a "write only" language.
> IMHO ???
Im my humble opinion.

> I don't disagree, but it is non-standard at present and therefore not
> portable. That is fine if you're not interested in portability but
> useless to those who are. If you feel that strongly about it raise an
> RfD to get the standard changed.
True, I'm not denying that. Never did. That's why I posed the question in
the first place. That's what I'm trying to test: is there room for an RfD
or can I better spend my time on something else.

> To me that is unnecessarily pedantic and rather silly.
To me it is rather silly to use COUNT for anything less than to get the
length of a string. That's the beauty of an opinion: everyone can have one.

> What has that got to do with this discussion? C@+ isn't a standard word,
> why should someone use it just because you prefer it.
Sorry, I tend to get carried away. What I *originally* was trying to do is
to illustrate why I think DOES> in interpretation mode is a cool idea.
Again, sorry I got lost ;-)

Hans Bezemer

Gerry Jackson

unread,
Dec 1, 2011, 10:35:27 AM12/1/11
to
On 01/12/2011 13:28, Hans Bezemer wrote:
>>> In your version the connection between this unnamed pointer array and the
>>> following definition is unclear. PASS is non-standard,
>> On the contrary it *is* standard ANS Forth, unlike your code.
> Never saw it in the standard (leafing) Nope, it's not there.

Sorry, I thought you meant that the *definition* of PASS was not
standard Forth. Of course it is not a standard word itself, I never
meant to imply that.


--
Gerry

BruceMcF

unread,
Dec 1, 2011, 12:32:53 PM12/1/11
to
On Dec 1, 2:25 am, "Ed" <nos...@invalid.com> wrote:

> The purpose of  DOES> in forth is to allow creation of defining words.
> Definers consist of two parts - a compile-time part and run-time part,
> in the form:

>     A.6.1.1250 DOES>

>     Typical use: : X ... DOES> ... ;

That is the form for the typical use, yes.

> DOES> terminates the compile-time part of the current definition
> (the definer) and appends the subsequent run-time semantics to
> the child CREATEd by the compile-time part.

However, the Forth94 specification defines >DOES by its *behavior*
rather than by the form in which it is typically used.

That behavior is quite clearly spelled out: what it does when compiled
into a word, and what it does when the word that it is compiled into
executes it.

> Since .RNO doesn't have a compile-time part it's not a defining
> word.  Not being a definer, using  DOES> was illegal (IMO).

DOES> compiled into .RNO is required to perform the desired behavior
when .RNO executes, and so it is quite clearly compliant with the
standard. An implementation which does not provide that behavior
when .RNO is executed is a non-compliant implementation.

Its true that the CREATEd definition that DOES> modifies is
*typically* created by the definition containing DOES> ... but to be
*constrained* to that use, the constraint would have to be in the
specification of DOES>

IOW:
: <name> ... CREATE ... DOES> ... ;
... is not a syntax. Its the result of the behavior of CREATE and the
behavior of DOES>

Andrew Haley

unread,
Dec 1, 2011, 1:19:49 PM12/1/11
to
Alex McDonald <bl...@rivadpm.com> wrote:
> On Nov 29, 8:09?am, "Elizabeth D. Rather" <erat...@forth.com> wrote:
>
>> It did not make array into a new defining word with the desired
>> indexing behavior, so even though it appeared to do something
>> appropriate with myarray, it didn't fulfill the purpose for which
>> DOES> exists.
>
> The spec doesn't talk of a purpose for DOES>, and only of typical use
> in the appendix; although that may have been the TC's intent.

Well, Elizabeth was there when DOES> was invented, so she certainly is
in a good position to know what its purpose is.

Andrew.

Alex McDonald

unread,
Dec 1, 2011, 1:58:36 PM12/1/11
to
On Dec 1, 6:19 pm, Andrew Haley <andre...@littlepinkcloud.invalid>
wrote:
Yes. But the intent is unrecorded in the specification.

Elizabeth D. Rather

unread,
Dec 1, 2011, 2:08:45 PM12/1/11
to
On 11/30/11 6:55 AM, Hans Bezemer wrote:

...
> Well, I particularly don't like HERE in user programs. When used in compiler
> words, ok, but not in my main program if I can avoid it.

HERE is actually more appropriate in user programs than in compiler
words, since it returns the address of the next location in *data
space*. It is entirely appropriate for user programs to manipulate data
space.

> As Paysan correctly stated, there is no doubt what an interpreted DOES>
> should do - and he proved it by doing it. Others, included myself of
> course, have shown that it is not merely a quirk but it can be used in real
> life programs with added benefits.

The benefits of doing this explicitly, rather than defining a defining
word to make your array, is unclear to me.

> But I think the difference between our coding styles shows by using 2DUP. In
> some systems that may be a primitive with added (though small) performance
> benefits. In others it is simply : 2DUP OVER OVER ; with speed penalties. I
> use 2DUP only when there is either a double number OR an address/count pair
> to be handled - even when that means a speed penalty, simply because I want
> to express that I'm handling two associated items. If not, I use OVER OVER
> just to signal these are two UNassociated items.

The '2' prefix is intended to convey precisely the fact that there is no
special relationship between the two items (in contrast to the 'D'
prefix, which specifies that the arguments are a double integer).

...
> Low bugcounts and palletable modification times are closely associated with
> clear coding. Obfuscated programming is an art in itself, but not very
> valuable IRL.

Yes, I agree. But individuals differ as to what is clear. To me, a
defining word called ARRAY (assuming, of course, that its existence and
behavior is documented) would be much clearer than your explicit use of
DOES>.

Elizabeth D. Rather

unread,
Dec 1, 2011, 2:10:52 PM12/1/11
to
Well, but I agree that it's information that shouldn't require my being
around to document! The intent of usage examples is to show the purpose
of a word or construction.

Alex McDonald

unread,
Dec 1, 2011, 2:12:41 PM12/1/11
to
On Nov 30, 12:14 am, "Ed" <nos...@invalid.com> wrote:
The bit you missed is;

Run-time: ( --) ( R: nest-sys1 --)
Replace the execution semantics of the *** most recent definition ***,
referred to as name, with the name execution semantics given below.
Return control to the calling definition specified by nest-sys1. An
ambiguous condition exists if name was not defined with *** CREATE or
a user-defined word that calls CREATE ***.

(My emphasis) That makes all the following valid;

: x create , does> @ ;

: doesbit does> @ ;
: x create , doesbit ;

: x create , does> @ does> @ 1+ ;

: doubledoes does> @ does> @ 1+ ;
: x create , doubledoes ;

: createbit create , ;
: doesbit does> @ ;
: x createbit doesbit ;

Ed

unread,
Dec 1, 2011, 9:52:20 PM12/1/11
to
Alex McDonald wrote:
> On Nov 30, 12:14Â am, "Ed" <nos...@invalid.com> wrote:
> > Alex McDonald wrote:
> > > On Nov 29, 5:49 am, "A. K." <a...@nospam.org> wrote:
> > > > On 29.11.2011 04:18, Bee wrote:
> >
> > > > > But should be is:
> >
> > > > > : .rno ( -- ) \ Radix Number Output
> > > > > DOES> C@ BASE @>R BASE ! U. R> BASE ! ;
> >
> > > > You are making a silent assumption here that DOES> works without CREATE:
> >
> > > > 6.1.1250 DOES>
> > > > does CORE
> > > > ...
> > > > An ambiguous condition exists if name was not defined with CREATE or a
> > > > user-defined word that calls CREATE.
> >
> > > You missed what followed?
> >
> > > CREATE .B ( n -- ) Â 2 C, .rno
> > > ^^^^^^
> >
> > .RNO Â didn't CREATE the current definition so all bets are off.
> >
> > Â Â 6.1.1250 DOES>
> > Â Â ...
> > Â Â Compilation: ( C: colon-sys1 -- colon-sys2 )
> >
> > Â Â Append the run-time semantics below to the current definition. ...
>
> The bit you missed is;
>
> Run-time: ( --) ( R: nest-sys1 --)
> Replace the execution semantics of the *** most recent definition ***,
> referred to as name, with the name execution semantics given below.
> Return control to the calling definition specified by nest-sys1. An
> ambiguous condition exists if name was not defined with *** CREATE or
> a user-defined word that calls CREATE ***.
>
> (My emphasis) That makes all the following valid;
>
> : x create , does> @ ;

Yes. It's a defining word in the classic form.

> : doesbit does> @ ;
> : x create , doesbit ;
>
> : x create , does> @ does> @ 1+ ;
>
> : doubledoes does> @ does> @ 1+ ;
> : x create , doubledoes ;
>
> : createbit create , ;
> : doesbit does> @ ;
> : x createbit doesbit ;

IMO most if not all these are suspect as they don't follow that
specified in Forth-79/83 DOES>

: <namex> ... <create> ... DOES> ... ;

i.e. there is one <create> and one DOES> and both words
appear in the body of the definer. Forth-94 hasn't contradicted
this, nor did they signal an intent to vary it AFAIK.

If there is something to be gained in the examples shown,
I'm failing to see it. If there is benefit, then have it explicitly
written into 200x and no-one will be confused.



BruceMcF

unread,
Dec 2, 2011, 12:55:05 AM12/2/11
to
On Dec 1, 2:10 pm, "Elizabeth D. Rather" <erat...@forth.com> wrote:
> Well, but I agree that it's information that shouldn't require
> my being around to document!  The intent of usage examples is
> to show the purpose of a word or construction.

However, it should *not* be assumed that the specification is subject
to amendment or modification at whim *except for* the aspects of the
specification shown in a usage example.

BruceMcF

unread,
Dec 2, 2011, 12:51:56 AM12/2/11
to
On Dec 1, 9:52 pm, "Ed" <nos...@invalid.com> wrote:
> If there is something to be gained in the examples shown,
> I'm failing to see it.  If there is benefit, then have it explicitly
> written into 200x and no-one will be confused.

It was explicitly written into Forth94, and that is not enough to
prevent the confusion.

Indeed, what relevance is it whether or not you see the benefit? The
fact is that the specification *spells out* what DOES> does, and as
DOES> is specified, then the following is supported by a standard-
compliant DOES>

\ Self-pushing wordlist
:noname ( o: -- wid ) DOES> @ >R GET-ORDER R> SWAP 1+ SET-ORDER ;

\ []niclos is only word added to original compilation wordlist
WORDLIST CREATE []niclos , DUP EXECUTE

GET-CURRENT []niclos DEFINITIONS

\ ...

... and its supported by a standard compliant DOES> whether or not you
think there is any *benefit* from *doing* that. The discussion of
whether the rationale for a 200x proposal is one thing, but the issue
here is something that was already decided on and specified in
Forth94. Whether or not there *was* a benefit resulting from whomever
it was who won *whatever* argument there was for specifying it that
way, is now very much water under the bridge.

Hans Bezemer

unread,
Dec 2, 2011, 3:28:06 AM12/2/11
to
BruceMcF wrote:
> Its true that the CREATEd definition that DOES> modifies is
> typically created by the definition containing DOES> ... but to be
> constrained to that use, the constraint would have to be in the
> specification of DOES>
>
> IOW:
>    : <name> ... CREATE ... DOES> ... ;
> ... is not a syntax. Its the result of the behavior of CREATE and the
> behavior of DOES>

So true. It is for that reason that I'd like to have seen a somewhat more
elaborate rationale for DOES>, just because there are some aspects that
are left dangling in the air, e.g. what is the state of the word that
CREATE leaves and until which point it is left in a state that makes its
behavior modifiable by DOES>:

:NONAME DOES> DUP @ SWAP CELL+ DUP @ SWAP CELL+ DUP @ + + ;

CREATE mything                  ( should be complete right now)
0 ,                             ( still modifiable, I guess)
HERE                            ( still modifiable, I guess)
DUP                             ( still modifiable, I guess)
>R                              ( still modifiable, I guess)
R>                              ( still modifiable, I guess)
, ,                             ( still modifiable, I guess)
: MORE ;                        ( OK, you had your chance)

Now the only thing we know is that when you use it in a definition
together with CREATE or a user defined word which uses CREATE you
should be fine.

Hans Bezemer

JennyB

unread,
Dec 2, 2011, 9:23:23 AM12/2/11
to han...@xs4all.nl
On Friday, 2 December 2011 08:28:06 UTC, Hans Bezemer wrote:
> So true. It is for that reason that I'd like to have seen a somewhat more
> elaborate rationale for DOES>, just because there are some aspects that
> are left dangling in the air, e.g. what is the state of the word that
> CREATE leaves and until which point it is left in a state that makes its
> behavior modifiable by DOES>:
>
> :NONAME DOES> DUP @ SWAP CELL+ DUP @ SWAP CELL+ DUP @ + + ;
>
> CREATE mything                  ( should be complete right now)
> 0 ,                             ( still modifiable, I guess)
> HERE                            ( still modifiable, I guess)
> DUP                             ( still modifiable, I guess)
> >R                              ( still modifiable, I guess)
> R>                              ( still modifiable, I guess)
> , ,                             ( still modifiable, I guess)

Why not? And BTW, how at this point would DOES> know if that CREATE had been executed from the same definition or not?

> : MORE ;                        ( OK, you had your chance)

Of course. because MYTHING is no longer the most recent definition. A Forth might possibly have DOES> use a variable set by the most recent CREATEd word, in which case the behaviour of MYTHING would still be set, but the only reason I can think of to allow that would be to get a weird recursion: MORE calls MYTHING and the DOES> part of MYTHING (defined after MORE) calls MORE.

That really makes my brain hurt! >;P

My guess is that for almost any Standard-ish Forth ever written, loading the above code and then EXECUTEing the :NONAME will cause it to try to attach the behaviour to MORE. Whether that raises an error or not is outside the Standard.

Andrew Haley

unread,
Dec 2, 2011, 11:44:37 AM12/2/11
to
Hans Bezemer <the...@xs4all.nl> wrote:
> BruceMcF wrote:
>> Its true that the CREATEd definition that DOES> modifies is
>> typically created by the definition containing DOES> ... but to be
>> constrained to that use, the constraint would have to be in the
>> specification of DOES>
>>
>> IOW:
>> : <name> ... CREATE ... DOES> ... ;
>> ... is not a syntax. Its the result of the behavior of CREATE and the
>> behavior of DOES>
>
> So true. It is for that reason that I'd like to have seen a somewhat more
> elaborate rationale for DOES>, just because there are some aspects that
> are left dangling in the air, e.g. what is the state of the word that
> CREATE leaves and until which point it is left in a state that makes its
> behavior modifiable by DOES>:

<<
6.1.1250 DOES>

...

Run-time: ( -- ) ( R: nest-sys1 -- )

Replace the execution semantics of the most recent definition,
referred to as name, with the name execution semantics given
below. Return control to the calling definition specified by
nest-sys1. An ambiguous condition exists if name was not defined with
CREATE or a user-defined word that calls CREATE.
>>

So, as long as the most most recent definition has been defined by
CREATE you'll be fine.

> :NONAME DOES> DUP @ SWAP CELL+ DUP @ SWAP CELL+ DUP @ + + ;
>
> CREATE mything ( should be complete right now)
> 0 , ( still modifiable, I guess)
> HERE ( still modifiable, I guess)
> DUP ( still modifiable, I guess)
>>R ( still modifiable, I guess)
> R> ( still modifiable, I guess)
> , , ( still modifiable, I guess)
> : MORE ; ( OK, you had your chance)

That's entirely correct.

> Now the only thing we know is that when you use it in a definition
> together with CREATE or a user defined word which uses CREATE you
> should be fine.

But the specification is much clearer than that.

Andrew.

Anton Ertl

unread,
Dec 2, 2011, 11:51:31 AM12/2/11
to
Andrew Haley <andr...@littlepinkcloud.invalid> writes:
>Well, Elizabeth was there when DOES> was invented, so she certainly is
>in a good position to know what its purpose is.

Since when does the purpose for which a feature was invented have any
significance? Ok, it may help interpret the specification in cases
where the specification is unclear, but in the case of DOES>, the
specification is clear and unambiguous.

- anton
--
M. Anton Ertl http://www.complang.tuwien.ac.at/anton/home.html
comp.lang.forth FAQs: http://www.complang.tuwien.ac.at/forth/faq/toc.html
New standard: http://www.forth200x.org/forth200x.html
EuroForth 2011: http://www.euroforth.org/ef11/

Andrew Haley

unread,
Dec 2, 2011, 12:42:42 PM12/2/11
to
Anton Ertl <an...@mips.complang.tuwien.ac.at> wrote:
> Andrew Haley <andr...@littlepinkcloud.invalid> writes:
>>Well, Elizabeth was there when DOES> was invented, so she certainly
>>is in a good position to know what its purpose is.
>
> Since when does the purpose for which a feature was invented have any
> significance?

When its purpose is the subject being discussed.

> Ok, it may help interpret the specification in cases where the
> specification is unclear, but in the case of DOES>, the
> specification is clear and unambiguous.

It is.

Andrew.

BruceMcF

unread,
Dec 2, 2011, 1:06:25 PM12/2/11
to
On Dec 2, 3:28 am, Hans Bezemer <theb...@xs4all.nl> wrote:
> So true. It is for that reason that I'd like to have seen a somewhat more
> elaborate rationale for DOES>, just because there are some aspects that
> are left dangling in the air, e.g. what is the state of the word that
> CREATE leaves and until which point it is left in a state that makes
> its behavior modifiable by DOES>:

Until there is a definition. If you know the most recent definition
was CREATEd, it is modified by DOES> ... if you don't know whether the
most recent definition was CREATEd, its up to the individual
implementation what happens.

That is:

:NONAME DOES> DUP @ SWAP CELL+ DUP @ SWAP CELL+ DUP @ + + ;
VOCABULARY []Niclos EXECUTE

... in an implementation that builds VOCABULARY with CREATE, it'll
modify vocabulary, in an implementation that does NOT build VOCABULARY
with CREATE ... it is allowed to (1) modify the most recent definition
that WAS created with CREATE or to (2) wreck VOCABULARY by treating it
as if it was created with created and put the DOES> patch somewhere
that it messes things up.

Which is why it can't portably:

VOCABULARY []Niclos
:NONAME DOES> DUP @ SWAP CELL+ DUP @ SWAP CELL+ DUP @ + +
; EXECUTE

:NONAME creates a definition, and so the "most recent definition"
would apply to the :NONAME. That wouldn't have been CREATEd, but an
implementation is free to have it built in a way DOES> would indeed
work for it.

Typically CREATE stores the patch location or address that gets to the
patch location in a state variable, and DOES> uses that patch
location, and for an implementation like that, any definition which
did not use CREATE is simply passed over. But that can only be assumed
for source dedicated to that implementation.

BruceMcF

unread,
Dec 2, 2011, 1:17:25 PM12/2/11
to
On Dec 2, 9:23 am, JennyB <jennybr...@googlemail.com> wrote:
> but the only reason I can think of to allow that would be to get a weird recursion: MORE calls MYTHING and the DOES> part of MYTHING (defined after MORE) calls MORE. ...

A more likely reason for allowing that is that in the context of that
implementation, CREATE is a perfectly fine factor for : and as long as
DOES> is used only on definitions EXPLICITLY made with CREATE there is
no problem.

Indeed, that is the point of the Forth94 spec ~ if CREATE is a useful
factor for : VARIABLE CONSTANT etc the standard respects that those
*might* have been created, if CREATE is a useful factor for VARIABLE
but not for : or CONSTANT (eg, HEADER is a common factor for all of
them but what CREATE does afterward is not useful for colon
definitions or constants) ... then the standard respects that those
*might not* have been made via ``CREATE''.

The spec in the standard lets the source author know where you *can*
reliably use a compliant DOES> and lets the implementer know where
there is leeway for implementations to do as they wish.

Hans Bezemer

unread,
Dec 2, 2011, 1:40:05 PM12/2/11
to
BruceMcF wrote:
> Indeed, that is the point of the Forth94 spec ~ if CREATE is a useful
> factor for : VARIABLE CONSTANT etc the standard respects that those
> *might* have been created, if CREATE is a useful factor for VARIABLE
> but not for : or CONSTANT (eg, HEADER is a common factor for all of
> them but what CREATE does afterward is not useful for colon
> definitions or constants) ... then the standard respects that those
> *might not* have been made via ``CREATE''.

Fun, the only way to write this portably is to refrain from the use of
VARIABLE and CONSTANT and write those things yourself:

: +CONSTANT CREATE , DOES> @ + ;
: +VARIABLE CREATE 1 CELLS ALLOT DOES> @ + ;

Instead of the more readable:

: +CONSTANT CONSTANT DOES> @ + ;
: +VARIABLE VARIABLE DOES> @ + ;

OK, that's how it is.. But I really expected that much ;-)

Hans




Elizabeth D. Rather

unread,
Dec 2, 2011, 2:35:05 PM12/2/11
to
On 12/2/11 4:23 AM, JennyB wrote:
> On Friday, 2 December 2011 08:28:06 UTC, Hans Bezemer wrote:
>> So true. It is for that reason that I'd like to have seen a somewhat more
>> elaborate rationale for DOES>, just because there are some aspects that
>> are left dangling in the air, e.g. what is the state of the word that
>> CREATE leaves and until which point it is left in a state that makes its
>> behavior modifiable by DOES>:
>>
>> :NONAME DOES> DUP @ SWAP CELL+ DUP @ SWAP CELL+ DUP @ + + ;
>>
>> CREATE mything ( should be complete right now)
>> 0 , ( still modifiable, I guess)
>> HERE ( still modifiable, I guess)
>> DUP ( still modifiable, I guess)
>> | R ( still modifiable, I guess)
>> R> ( still modifiable, I guess)
>> , , ( still modifiable, I guess)
>
> Why not? And BTW, how at this point would DOES> know if that CREATE
> had been executed from the same definition or not?

It doesn't. Which is why definitions such as the :NONAME example here
are legal (although I'm not sure it's useful to separate them like that).

But I want to make the point that the operators following CREATE mything
above are entirely atomic: they are modifying or referencing data space,
and the fact that they occur immediately after CREATE has defined a word
pointing to the start of that data space gives access to it, but these
actions aren't part of a definition.

Also, of course, it's not legal to do whatever this is trying to do to
the Return Stack interpretively.

>> : MORE ; ( OK, you had your chance)
>
> Of course. because MYTHING is no longer the most recent definition.

Right. In an implementation with separate dictionary and data space,
you might still use , and friends to modify data space (though with a
dependency on the segregation), but you can no longer use DOES> to
modify the behavior of MYTHING.

> A Forth might possibly have DOES> use a variable set by the most
> recent CREATEd word, in which case the behaviour of MYTHING would
> still be set, but the only reason I can think of to allow that would
> be to get a weird recursion: MORE calls MYTHING and the DOES> part
> of MYTHING (defined after MORE) calls MORE.
>
> That really makes my brain hurt!>;P

As it should, because it's illegal. There's a reason the Standard says
"...the most recent definition" without specifying what kind of definition.

> My guess is that for almost any Standard-ish Forth ever written,
> loading the above code and then EXECUTEing the :NONAME will cause
> it to try to attach the behaviour to MORE. Whether that raises an
> error or not is outside the Standard.

Yes, it's a classical "ambiguous condition".

>> Now the only thing we know is that when you use it in a definition
>> together with CREATE or a user defined word which uses CREATE you
>> should be fine.

As Andrew points out, you really do know more than that.

Albert van der Horst

unread,
Dec 2, 2011, 7:58:28 PM12/2/11
to
In article <4ed91b48$0$6840$e4fe...@news2.news.xs4all.nl>,
I find this thoroughly unreadable.
Then, it doesn't work in my Forth.
I have this mental picture of a CREATE DOES> word that
requires two data area's, the body and the high level
code. (As per ISO.)

A constant requires one data area to contain it.
The sequence CONSTANT DOES> is mere puzzling.
A variable requires one data area whose address can be
used. Ditto.

>
>OK, that's how it is.. But I really expected that much ;-)

>
>Hans

Groetjes Albert

--
--
Albert van der Horst, UTRECHT,THE NETHERLANDS
Economic growth -- being exponential -- ultimately falters.
albert@spe&ar&c.xs4all.nl &=n http://home.hccnet.nl/a.w.m.van.der.horst

Elizabeth D. Rather

unread,
Dec 2, 2011, 11:33:18 PM12/2/11
to
On 12/2/11 2:58 PM, Albert van der Horst wrote:
> In article<4ed91b48$0$6840$e4fe...@news2.news.xs4all.nl>,
> Hans Bezemer<han...@xs4all.nl> wrote:
>> BruceMcF wrote:
>>> Indeed, that is the point of the Forth94 spec ~ if CREATE is a useful
>>> factor for : VARIABLE CONSTANT etc the standard respects that those
>>> *might* have been created, if CREATE is a useful factor for VARIABLE
>>> but not for : or CONSTANT (eg, HEADER is a common factor for all of
>>> them but what CREATE does afterward is not useful for colon
>>> definitions or constants) ... then the standard respects that those
>>> *might not* have been made via ``CREATE''.
>>
>> Fun, the only way to write this portably is to refrain from the use of
>> VARIABLE and CONSTANT and write those things yourself:
>>
>> : +CONSTANT CREATE , DOES> @ + ;
>> : +VARIABLE CREATE 1 CELLS ALLOT DOES> @ + ;
>>
>> Instead of the more readable:
>>
>> : +CONSTANT CONSTANT DOES> @ + ;
>> : +VARIABLE VARIABLE DOES> @ + ;
>
> I find this thoroughly unreadable.
> Then, it doesn't work in my Forth.
> I have this mental picture of a CREATE DOES> word that
> requires two data area's, the body and the high level
> code. (As per ISO.)

Suppose CONSTANT is defined this way:

: CONSTANT ( n -- ) CREATE , DOES> ( -- n ) @ ;

...which is a perfectly reasonable and legal way to define CONSTANT.
Then Albert's definitions would work just fine. He sees it as readable
since he knows his CONSTANT is equivalent to the definition above. It is
readable if you know that CONSTANT defines a pre-initialized data space
with a semantics that can be replaced (since it was defined with
CREATE). Portability, however, requires acknowledging that there are
many other ways to define CONSTANT, such as a word that compiles a
literal in definitions, etc., in which case this wouldn't work.

> A constant requires one data area to contain it.
> The sequence CONSTANT DOES> is mere puzzling.
> A variable requires one data area whose address can be
> used. Ditto.

How? Why should CONSTANT DOES> word require more than one data area?
Mainly it requires a structure that allows the associated semantics to
be replaced, which is true if it's defined as in my example, but not
necessarily otherwise.

Ed

unread,
Dec 3, 2011, 3:56:02 AM12/3/11
to
Hans Bezemer wrote:
> BruceMcF wrote:
> > Its true that the CREATEd definition that DOES> modifies is
> > typically created by the definition containing DOES> ... but to be
> > constrained to that use, the constraint would have to be in the
> > specification of DOES>
> >
> > IOW:
> > Â Â : <name> ... CREATE ... DOES> ... ;
> > ... is not a syntax. Its the result of the behavior of CREATE and the
> > behavior of DOES>
>
> So true.

The syntax came first. Because Forth-79/83 never explained in detail what
going on with

: x <create> ... DOES> ... ;

Forth-94 had the unenviable task of documenting it.

Now folks want to reverse-engineer the spec - which was only ever meant
to document the syntax - and use it to extract some "legal" usage based on
their interpretation. What they're engaging in is extrapolation.

It may be fun finding some new "use" for the old dog that no-one thought of.
But before I'd impose it on everyone as a requirement, I'd want to be sure
it was of consequence and provided real utility beyond what the original
offered.

My challenge is this. Don't tell me what's legal - show me what's undeniably
useful.



BruceMcF

unread,
Dec 3, 2011, 1:02:10 PM12/3/11
to
On Dec 3, 3:56 am, "Ed" <nos...@invalid.com> wrote:
> Hans Bezemer wrote:
>> BruceMcF wrote:
>>> IOW:
>>> : <name> ... CREATE ... DOES> ... ;
>>> ... is not a syntax. Its the result of the behavior of CREATE and the
>>> behavior of DOES>

> The syntax came first.

No, the behavior came first. CREATE DOES> was an upgrade to <BUILD
DOES> and the behavior was understood in the context of a 70's style
indirect threaded implementation.

> Because Forth-79/83 never explained in detail what
> going on with
>
>     : x  <create> ... DOES> ... ;
>
> Forth-94 had the unenviable task of documenting it.

Forth79/83 were standardizing an already existing programming
technique.

> Now folks want to reverse-engineer the spec - which was only ever
> meant to document the syntax - and use it to extract some "legal"
> usage based on their interpretation.

That's a fine theory, but under the original CREATE DOES> what you are
calling "reverse engineering the spec" *already* worked for (assuming
IF/THEN works in interpret, as it did for some implementations):

: single-doer ( -- ) @ + side ! ;
: double-doer ( -- ) 2@ D+ side 2! ;
...

CREATE data-bytes DUP ALLOT
2 = IF single-doer ELSE double-doer doer32 THEN

DOES> patched the most recent definition, it didn't care whether the
CREATE that had made the definition was earlier in the same definition
or not.

BruceMcF

unread,
Dec 3, 2011, 5:56:45 PM12/3/11
to
On Dec 3, 1:02 pm, BruceMcF <agil...@netscape.net> wrote:

> : single-doer ( -- ) @ + side ! ;
> : double-doer ( -- ) 2@ D+ side 2! ;
> ...

> CREATE data-bytes DUP ALLOT
> 2 = IF single-doer ELSE double-doer doer32 THEN

CREATE side++ data-bytes DUP ALLOT
2 = IF single-doer ELSE double-doer doer32 THEN

And we don't even know what evil-doer does> even if we suspect we wish
to stop it from being done.

Rod Pemberton

unread,
Dec 3, 2011, 7:22:52 PM12/3/11
to
"BruceMcF" <agi...@netscape.net> wrote in message
news:688f3314-6aec-467a...@q16g2000yqn.googlegroups.com...
> On Dec 3, 3:56 am, "Ed" <nos...@invalid.com> wrote:
>
> > Now folks want to reverse-engineer the spec - which was only ever
> > meant to document the syntax - and use it to extract some "legal"
> > usage based on their interpretation.
>
> That's a fine theory, but under the original CREATE DOES> what you are
> calling "reverse engineering the spec" *already* worked for (assuming
> IF/THEN works in interpret, as it did for some implementations):

If there were a set of test(s) that confirmed "standard behavior" and
"typical behavior" for CREATE DOES>, then I doubt implementors would be
having these problems. Got any? It took me quite a while to figure out how
to implement them. I know they work for simple stuff. If I hadn't been
implementing an interpreter, I probably never would've understood what
they do. I'm still not sure they work for more advanced or odd usage.
Adding "object oriented" like functionality in an era when "spaghetti" code
was the norm, and "structured programming" concepts were just ideas, was
either brilliant, insane, or just stupid luck ...


Rod Pemberton



Elizabeth D. Rather

unread,
Dec 4, 2011, 1:42:56 AM12/4/11
to
This is exactly the problem one runs into when you try to write a Forth
without first writing some Forth applications. If you first learn how
to *use* Forth effectively you will have much easier going if you want
to implement one.

Cheers,
Elizabth

BruceMcF

unread,
Dec 4, 2011, 1:42:47 PM12/4/11
to
On Dec 3, 7:22 pm, "Rod Pemberton" <do_not_h...@noavailemail.cmm>
wrote:
> If there were a set of test(s) that confirmed "standard behavior" and
> "typical behavior" for CREATE DOES>, then I doubt implementors would be
> having these problems.

I hadn't seen any evidence that this was about implementers having any
problems. It is, after all, *easier* to implement the CREATE DOES>
system as a set of behavior than to try to implement it as a syntax.

Somewhere down there, you have a dictionary entry creating factor.
Have it store its location in a variable, LASTDEF.

Write a word that can translate from the dictionary entry to where the
patch for DOES> is supposed to go when CREATE is the word that used
that factor ...
>DOES-SPOT ( addr -- addr )

Design DODOES so it handles whatever magic is required to get
interpretation going on the high level code after a call to DODOES.
With direct threading, there might be a ``CALL,'' required before that
address.

And you've got to exit the word that DOES> appears in.

So its something like ...
POSTPONE EXIT HERE LASTDEF @ >DOES-SPOT ! ' DODOES COMPILE,
... or ...
POSTPONE EXIT HERE LASTDEF @ >DOES-SPOT ! CALL, ' DODOES ,

As soon as your DODOES works *at all*, it'll work whenever DOES> is
supposed to work under the standard.

Ed

unread,
Dec 4, 2011, 10:15:03 PM12/4/11
to
Rod Pemberton wrote:
> ...
> If there were a set of test(s) that confirmed "standard behavior" and
> "typical behavior" for CREATE DOES>, then I doubt implementors would be
> having these problems. Got any? It took me quite a while to figure out how
> to implement them. I know they work for simple stuff. If I hadn't been
> implementing an interpreter, I probably never would've understood what
> they do.

I agree. The Forth-94 spec for DOES> is difficult going. I doubt I
could have implemented it, or understood what it was intended to
do, just by reading the spec proper.

In practice one sees how CREATE DOES> has been traditionally
used, and access to free forth systems and source tells one how
to implement it.

> I'm still not sure they work for more advanced or odd usage.

If there are advanced uses, they are conspicuous by their absence.
After 40 years these surely would have been found and passed into
common usage.

Exploiting wording in the Standard to elicit "new uses" is a favourite
c.l.f. pastime. Thankfully most are quickly forgotten - though not
before leaving users with the impression Forth is complicated.



Alex McDonald

unread,
Dec 5, 2011, 12:51:58 AM12/5/11
to
On Dec 4, 10:15 pm, "Ed" <nos...@invalid.com> wrote:
> Rod Pemberton wrote:
> > ...
> > If there were a set of test(s) that confirmed "standard behavior" and
> > "typical behavior" for CREATE DOES>, then I doubt implementors would be
> > having these problems.  Got any?  It took me quite a while to figure out how
> > to implement them.  I know they work for simple stuff.  If I hadn't been
> > implementing an interpreter, I probably never would've understood what
> > they do.
>
> I agree.  The Forth-94 spec for DOES> is difficult going.  I doubt I
> could have implemented it, or understood what it was intended to
> do, just by reading the spec proper.

The same can be said for any specification; they aren't intended as
tutorials, but they do document defined behaviour.

>
> In practice one sees how CREATE DOES> has been traditionally
> used, and access to free forth systems and source tells one how
> to implement it.
>
> > I'm still not sure they work for more advanced or odd usage.

They do. If they don't work in your Forth, then DOES> is broken in
your Forth.

>
> If there are advanced uses, they are conspicuous by their absence.
> After 40 years these surely would have been found and passed into
> common usage.

Since the issue you were having with CREATE and DOES> in separate
words is common usage, it's perhaps down to experience and lack of
necessity in your code. Here's a sample from the Win32Forth
disassembler;

: opstr ( -- "name" )
create parse-str ", ;

\ OPSTR is a CREATE for a counted string.

: inh ( -<name>- )
opstr does> count (.sop") drop ;
inh clc "clc"
inh stc "stc"
( more opcodes without operands... )

: str ( addr code -- addr' )
opstr does> oper-col count type bit0 if ." d" else ." b" then
cmnt-col ;
str mvs "movs"
str cps "cmps"
( more string opcodes... )

: pre ( -<name>- )
opstr does> oper-col count type space drop true to dis.prefix-
op ;
pre cs: "cs:"
pre ds: "ds:"
( more prefixes; and so on... )


INH STR and PRE (and many others for various instruction types) share
a factored out OPSTR that does the common CREATE, while INH STR and
PRE have different actions. How would you propose doing this?

>
> Exploiting wording in the Standard to elicit "new uses" is a favourite
> c.l.f. pastime.  Thankfully most are quickly forgotten - though not
> before leaving users with the impression Forth is complicated.

Only if you insist it's so. See above.

David N. Williams

unread,
Dec 5, 2011, 7:10:42 PM12/5/11
to
3wOn 12/3/11 7:22 PM, Rod Pemberton wrote:
> "BruceMcF"<agi...@netscape.net> wrote in message
> news:688f3314-6aec-467a...@q16g2000yqn.googlegroups.com...
>> On Dec 3, 3:56 am, "Ed"<nos...@invalid.com> wrote:
>>
>>> Now folks want to reverse-engineer the spec - which was only ever
>>> meant to document the syntax - and use it to extract some "legal"
>>> usage based on their interpretation.
>>
>> That's a fine theory, but under the original CREATE DOES> what you are
>> calling "reverse engineering the spec" *already* worked for (assuming
>> IF/THEN works in interpret, as it did for some implementations):
>
> If there were a set of test(s) that confirmed "standard behavior" and
> "typical behavior" for CREATE DOES>, then I doubt implementors would be
> having these problems. Got any?

Don't the usual Hayes core tests qualify? They even include
"weird" behavior for DOES>.

-- David

Arnold Doray

unread,
Dec 6, 2011, 9:23:01 AM12/6/11
to
I'm not sure what your point is with this example ...

The '94 spec is crystal clear that DOES> needs to be preceded by a
CREATE. They don't necessarily have to be in the same definition. INH, STR
and PRE all follow a CREATE by a DOES>. Isn't this plain vanilla '94 spec?

Cheers,
Arnold

Alex McDonald

unread,
Dec 6, 2011, 10:05:57 AM12/6/11
to
Yes, and that's the point, since Ed was claiming that this kind of
usage is (a) not permitted by the spec, for which see his posts
upthread and (b) far too fancy pants for mere mortals.

Anton Ertl

unread,
Dec 6, 2011, 10:40:28 AM12/6/11
to
Andrew Haley <andr...@littlepinkcloud.invalid> writes:
>Anton Ertl <an...@mips.complang.tuwien.ac.at> wrote:
>> Andrew Haley <andr...@littlepinkcloud.invalid> writes:
>>>Well, Elizabeth was there when DOES> was invented, so she certainly
>>>is in a good position to know what its purpose is.
>>
>> Since when does the purpose for which a feature was invented have any
>> significance?
>
>When its purpose is the subject being discussed.

If the subject is "the purpose for which it was invented", yes. In
general, the purpose depends on the particular usage, and is mostly
independent on the porpose for which it was invented.

Arnold Doray

unread,
Dec 6, 2011, 11:03:58 AM12/6/11
to
On Tue, 06 Dec 2011 07:05:57 -0800, Alex McDonald wrote:

>>
>> I'm not sure what your point is with this example ...
>>
>> The '94 spec is crystal clear that DOES> needs to be preceded by a
>> CREATE. They don't necessarily have to be in the same definition. INH,
>> STR and PRE all follow a CREATE by a DOES>. Isn't this plain vanilla
>> '94 spec?
>>
>> Cheers,
>> Arnold
>
> Yes, and that's the point, since Ed was claiming that this kind of usage
> is (a) not permitted by the spec, for which see his posts upthread and
> (b) far too fancy pants for mere mortals.

A more interesting version of your example is in the '94 spec. See page
150 on Section A.6.2.0455.

I've only just begun programming in Forth, and this usage doesn't (pun
intended) seem too hard to grasp. And it is obviously very useful.

What I find hard to grasp is why using DOES> alone in interpretative mode
is useful or desirable.

Cheers,
Arnold



Anton Ertl

unread,
Dec 6, 2011, 12:09:25 PM12/6/11
to
"Ed" <nos...@invalid.com> writes:
>I agree. The Forth-94 spec for DOES> is difficult going. I doubt I
>could have implemented it, or understood what it was intended to
>do, just by reading the spec proper.

The spec for DOES> is actually very implementation-oriented. You may
have difficulties because you are not familiar with the style and
language of the glossary entries in the standard. But as long as we
keep that, this is probably the easiest spec to understand for the
system implementor, certainly easier than a syntax-oriented approach
(that's fortunately rare in the standard, no example comes to my mind
at the moment. But nonsense like the message-sending in (LOCAL)
certainly did not help the understandability of that specification).

>In practice one sees how CREATE DOES> has been traditionally
>used, and access to free forth systems and source tells one how
>to implement it.

Sure, that's certainly a good basis. You read the standard if you
want to be correct in the corner cases, but it's not a tutorial,
neither for programmers nor for system implementors.

>If there are advanced uses, they are conspicuous by their absence.

You are always quick to claim that things don't exist that have
existed for a long time.

BruceMcF

unread,
Dec 6, 2011, 7:04:51 PM12/6/11
to
On Dec 6, 12:09 pm, an...@mips.complang.tuwien.ac.at (Anton Ertl)
wrote:
>>If there are advanced uses, they are conspicuous by their absence.

> You are always quick to claim that things don't exist that have
> existed for a long time.

Note that the early 1980's style of use that Ed is complaining about
(NB. in a counted-string " family of implementation):

CREATE Alex " Alex" $, do-name
CREATE Ohio " OH" $, do-state

... are anything but "advanced cases". Doing it in the interpreter is
just bench testing before:

: make-name ( "name" "string" -- ) CREATE BL WORD $, do-name ;
: make-state ( "name" "string" -- ) CREATE BL WORD $, do-state ;

Alex McDonald

unread,
Dec 6, 2011, 10:53:07 PM12/6/11
to
Wouldn't this be cool...

create it's-really-useful-to-have " an interpreted does>" $, does>
count ;

BruceMcF

unread,
Dec 7, 2011, 10:19:02 AM12/7/11
to
It might be cool, but as soon as you create more than one self-
counting counted string constant, its more convenient to:

: does-count DOES> count ;

CREATE it's-really-useful-to-have? " an interpreted does>" $, does-
count

... or:

CREATE it's-really-useful-to-have? does-count
" an interpreted does>" $,

... where:
CREATE it's-really-useful-to-have? does> COUNT ;
" an interpreted does>" $,
... cannot be done with "an interpreted does>" unless compile space
and data space are separate, because of the impact on the dictionary.

Hans Bezemer

unread,
Dec 7, 2011, 1:21:23 PM12/7/11
to
BruceMcF wrote:
> It might be cool, but as soon as you create more than one self-
> counting counted string constant, its more convenient to:
>
> : does-count DOES> count ;
>
> CREATE it's-really-useful-to-have? " an interpreted does>" $, does-
> count
>
> ... or:
>
> CREATE it's-really-useful-to-have? does-count
> " an interpreted does>" $,
>
> ... where:
> CREATE it's-really-useful-to-have? does> COUNT ;
> " an interpreted does>" $,
> ... cannot be done with "an interpreted does>" unless compile space
> and data space are separate, because of the impact on the dictionary.

Well, I may just be a bit of rewriting, but this works:

: S,
here over 1+ allot place align ; ok
create myomy s" This is my string" s, does> count type ; ok
myomy This is my string ok

Just like I would rather write:

create NULL 0 , does> @ ;

Instead of:

create NULL does> @ ; 0 ,

Hans Bezemer


Coos Haak

unread,
Dec 7, 2011, 2:58:16 PM12/7/11
to
Op Wed, 07 Dec 2011 19:21:23 +0100 schreef Hans Bezemer:
The last one does not work. The does> overwrites the xt, no problem, but
the @ and ; will file the paramater field. The 0 comes behind that and is
unfindable by the @.
At least in my implementation that is :-(

--
Coos

CHForth, 16 bit DOS applications
http://home.hccnet.nl/j.j.haak/forth.html

BruceMcF

unread,
Dec 7, 2011, 3:35:38 PM12/7/11
to
On Dec 7, 1:21 pm, Hans Bezemer <theb...@xs4all.nl> wrote:
> BruceMcF wrote:
> > It might be cool, but as soon as you create more than one self-
> > counting counted string constant, its more convenient to:
>
> > : does-count DOES> count ;
>
> > CREATE it's-really-useful-to-have? " an interpreted does>" $, does-
> > count
>
> > ... or:
>
> > CREATE it's-really-useful-to-have? does-count
> >    " an interpreted does>" $,
>
> > ... where:
> >    CREATE it's-really-useful-to-have? does> COUNT ;
> >       " an interpreted does>" $,
> > ... cannot be done with "an interpreted does>" unless compile space
> > and data space are separate, because of the impact on the dictionary.

> Well, I may just be a bit of rewriting, but this works:

> : S,
>   here over 1+ allot place align ; ok
> create myomy s" This is my string" s, does> count type ;  ok
> myomy This is my string ok

Yes, if interpreted DOES> words, then that word ... but that's not the
point I was trying to make.

The *point* of putting the modification right after the word has been
created is that you *can* do it if you it the long-established
ordinary way, while with an interpreted DOES> you are *constrained* to
putting it after you are done with the dataspace associated with the
CREATEd word.

As to why, it could be because the dataspace set-up is starting to get
more complicated, and you don't want to hide the setting of the word
action until after a complex structure has been defined, or you've
passed a string through a macro generator, or etc.

Its not that there's a pressing need to do it that way *all the time*,
but that doing it the normal way, you always have the *option* of
placing it where you think its clearer to someone reading the code.

Elizabeth D. Rather

unread,
Dec 7, 2011, 3:39:35 PM12/7/11
to
On 12/7/11 9:58 AM, Coos Haak wrote:
> Op Wed, 07 Dec 2011 19:21:23 +0100 schreef Hans Bezemer:
...
>> Just like I would rather write:
>>
>> create NULL 0 , does> @ ;
>>
>> Instead of:
>>
>> create NULL does> @ ; 0 ,
>>
>> Hans Bezemer
>
> The last one does not work. The does> overwrites the xt, no problem, but
> the @ and ; will file the paramater field. The 0 comes behind that and is
> unfindable by the @.
> At least in my implementation that is :-(

You are right, there is no guarantee that data space is contiguous when
you compile stuff.

From Forth94 3.3.3.2 Contiguous Regions:

"CREATE establishes the beginning of a contiguous region of data space,
whose starting address is returned by the CREATEd definition. This
region is terminated by compiling the next definition.

"Since an implementation is free to allocate data space for use by code,
the above operators need not produce contiguous regions of data space if
definitions are added to or removed from the dictionary between
allocations. An ambiguous condition exists if deallocated memory
contains definitions."

Cheers,
Elizabeth

Ed

unread,
Dec 7, 2011, 5:21:55 PM12/7/11
to
Alex McDonald wrote:
> On Dec 4, 10:15 pm, "Ed" <nos...@invalid.com> wrote:
> > ...
> > If there are advanced uses, they are conspicuous by their absence.
> > After 40 years these surely would have been found and passed into
> > common usage.
>
> Since the issue you were having with CREATE and DOES> in separate
> words is common usage, it's perhaps down to experience and lack of
> necessity in your code. Here's a sample from the Win32Forth
> disassembler;
>
> : opstr ( -- "name" )
> create parse-str ", ;
>
> \ OPSTR is a CREATE for a counted string.
>
> : inh ( -<name>- )
> opstr does> count (.sop") drop ;
> ...

No issue with this. INH is a defining word in the syntax specified by
Forth-83 and 94

: x <create> ... DOES> ... ;

> > Exploiting wording in the Standard to elicit "new uses" is a favourite
> > c.l.f. pastime. Thankfully most are quickly forgotten - though not
> > before leaving users with the impression Forth is complicated.
>
> Only if you insist it's so. See above.

I had in mind these examples.

: doesbit does> @ ;
: x create , doesbit ;

: x create , does> @ does> @ 1+ ;

: doubledoes does> @ does> @ 1+ ;
: x create , doubledoes ;

These have no common practice nor any practical value that
I can see, despite they may compile on many forths.

Factoring "DOES>" into another word serves no purpose
other than make defining words more difficult to recognize.

One DOES> in a definer is plentiful and sufficient. Anything
more is mind-boggling.

My challenge stands.



Hans Bezemer

unread,
Dec 7, 2011, 5:52:49 PM12/7/11
to
Coos Haak wrote:
> The last one does not work. The does> overwrites the xt, no problem, but
> the @ and ; will file the paramater field. The 0 comes behind that and is
> unfindable by the @.
> At least in my implementation that is :-(
I'm quite aware of that. It won't in mine either ;-)

It was the notation Bruce suggested - which was very "unnatural" to me.

Hans Bezemer

Ed

unread,
Dec 7, 2011, 5:57:47 PM12/7/11
to
Anton Ertl wrote:
> "Ed" <nos...@invalid.com> writes:
> ...
> >If there are advanced uses, they are conspicuous by their absence.
>
> You are always quick to claim that things don't exist that have
> existed for a long time.

I assume you have some examples. Bring them on.



BruceMcF

unread,
Dec 7, 2011, 5:59:15 PM12/7/11
to
On Dec 7, 5:21 pm, "Ed" <nos...@invalid.com> wrote:
> These have no common practice nor any practical value that
> I can see, despite they may compile on many forths.

Just as there is no practical value in "2DUP", since you can just say:
... OVER OVER ...
instead.

If you have a number of words, all with an identical "DOES> ... ;"
segment, naming that and putting it into a single definition is just
ordinary factoring. Each time you re-use that factor via a definition,
you save net dictionary space, so once you've saved the size of the
header, you're ahead.

If Forth83 wished to pretend that it was a syntax, well that was the
prerogative of the Forth83 committee ~ they did a lot of things that
various Forth programmers and implementers disagreed with ...

... and you may claim that Forth94 specifies a syntax, but the claim
is patently false, so it only undermines the credibility of the rest
of your argument.

I first started programming in Forth on a fig-Forth derived
implementation before the Forth83 standard was published, and I am
confident that somewhere in either Forth Dimensions, the Byte Forth
Issue, or Dr. Dobbs I read a description of the difference between
<BUILD DOES> and CREATE DOES> that was in terms of behavior, not
syntax, and under which the long established behavior that you find
mind-boggling was taken for granted as a normal use of the words.

Coos Haak

unread,
Dec 7, 2011, 7:00:42 PM12/7/11
to
Op Thu, 8 Dec 2011 09:21:55 +1100 schreef Ed:
I have words in my assembler written by someone else before 1994 that are
like this:
: <name> CREATE .. DOES> .. CREATE .. DOES> .. ;

To understand them took some time though. I have never had problem with
their behavior.

Ed

unread,
Dec 7, 2011, 7:16:48 PM12/7/11
to
David N. Williams wrote:
> 3wOn 12/3/11 7:22 PM, Rod Pemberton wrote:
> > ...
> > If there were a set of test(s) that confirmed "standard behavior" and
> > "typical behavior" for CREATE DOES>, then I doubt implementors would be
> > having these problems. Got any?
>
> Don't the usual Hayes core tests qualify? They even include
> "weird" behavior for DOES>.

So it DOES>

In fact *all* the Hayes DOES> tests are weird. There is not a single
test which tests : x <create> ... DOES> ... ;

Very strange.



BruceMcF

unread,
Dec 7, 2011, 9:12:10 PM12/7/11
to
On Dec 7, 7:16 pm, "Ed" <nos...@invalid.com> wrote:
> In fact *all* the Hayes DOES> tests are weird.  There is not a single
> test which tests   : x  <create> ... DOES>  ...  ;

But if the most recent definition was made by CREATE, and it has its
behavior correctly modified by DOES> when the word containing DOES> is
executed, what *difference* does it make if the CREATE was executed in
the same definition, in a different definition, or directly executed
in the command interpreter?

There is absolutely no reason why factoring ought to break the correct
execution behavior of DOES>

Alex McDonald

unread,
Dec 8, 2011, 2:12:31 AM12/8/11
to
On Dec 7, 5:21 pm, "Ed" <nos...@invalid.com> wrote:
> Alex McDonald wrote:
> > On Dec 4, 10:15 pm, "Ed" <nos...@invalid.com> wrote:
> > > ...
> > > If there are advanced uses, they are conspicuous by their absence.
> > > After 40 years these surely would have been found and passed into
> > > common usage.
>
> > Since the issue you were having with CREATE and DOES> in separate
> > words is common usage, it's perhaps down to experience and lack of
> > necessity in your code. Here's a sample from the Win32Forth
> > disassembler;
>
> > : opstr  ( -- "name" )
> >          create parse-str  ", ;
>
> > \ OPSTR is a CREATE for a counted string.
>
> > : inh   ( -<name>- )
> >         opstr does> count (.sop") drop ;
> > ...
>
> No issue with this.  INH is a defining word in the syntax specified by
> Forth-83 and 94

No. CREATE <name> is the defining word that DOES> refers to.

>
>     : x  <create> ... DOES> ... ;
>
> > > Exploiting wording in the Standard to elicit "new uses" is a favourite
> > > c.l.f. pastime. Thankfully most are quickly forgotten - though not
> > > before leaving users with the impression Forth is complicated.
>
> > Only if you insist it's so. See above.
>
> I had in mind these examples.
>
>     : doesbit does> @ ;
>     : x create , doesbit ;
>
>     : x create , does> @ does> @ 1+ ;
>
>     : doubledoes does> @ does> @ 1+ ;
>     : x create , doubledoes ;
>
> These have no common practice nor any practical value that
> I can see, despite they may compile on many forths.
>
> Factoring "DOES>" into another word serves no purpose
> other than make defining words more difficult to recognize.
>
> One DOES> in a definer is plentiful and sufficient.  Anything
> more is mind-boggling.
>
> My challenge stands.

Your challenge is to explain in terms of the Forth94 standards
specification of CREATE ... DOES> why they are invalid. If that's not
your claim, I shall assume that the statement that they are of "no
common practice nor any practical value" is just your personal opinion.

Gerry Jackson

unread,
Dec 8, 2011, 6:02:30 AM12/8/11
to
The argument that the <create> and DOES> must exist in the same
definition is undermined by the example code in section A.16.6.2.0715 of
the ANS Forth standard.

>
> Factoring "DOES>" into another word serves no purpose
> other than make defining words more difficult to recognize.
>

DOES> cannot be used in a control structure. It makes sense to factor
out the DOES> code if you want to do something like:

: x DOES> one-behaviour ;
: y DOES> another-behaviour ;
: z CREATE ... if x else y then ;

> One DOES> in a definer is plentiful and sufficient. Anything
> more is mind-boggling.

That may be true. But the GForth manual gives a real-life use for two
DOES>'s in one word, see section 5.9.8.3, but that usage does appear to
be non-standard Forth.

Multiple DOES>'s could be used for a state machine where each DOES> puts
the machine into the next state e.g.

defer sm
: init does> sm ;

:noname
cr ." State: " drop 1 .
does> drop 2 . does> drop 3 . does> drop 4 . init
; is sm

: fsm create init ;

fsm x
x x x x x x x
State: 1 2 3 4
State: 1 2 3 ok

Which would be more useful if DOES> could be used on any CREATEd word,
not just the last one which also has to be the most recent definition.

>
> My challenge stands.
>

I don't think so, unless I've lost sight of what the challenge actually was.

--
Gerry

Anton Ertl

unread,
Dec 8, 2011, 6:35:39 AM12/8/11
to
Gerry Jackson <ge...@jackson9000.fsnet.co.uk> writes:
>That may be true. But the GForth manual gives a real-life use for two
>DOES>'s in one word, see section 5.9.8.3, but that usage does appear to
>be non-standard Forth.

The example is (from
<http://www.complang.tuwien.ac.at/forth/gforth/Docs-html/Advanced-does_003e-usage-example.html>):

: define-format ( disasm-xt table-xt -- )
\ define an instruction format that uses disasm-xt for
\ disassembling and enters the defined instructions into table
\ table-xt
create 2,
does> ( u "inst" -- )
\ defines an anonymous word for disassembling instruction inst,
\ and enters it as u-th entry into table-xt
2@ swap here name string, ( u table-xt disasm-xt c-addr ) \ remember string
noname create 2, \ define anonymous word
execute lastxt swap ! \ enter xt of defined word into table-xt
does> ( addr w -- )
\ disassemble instruction w at addr
2@ >r ( addr w disasm-xt R: c-addr )
execute ( R: c-addr ) \ disassemble operands
r> count type ; \ print name

This example uses some non-standard words and is therefore
nonstandard, but the usage of DOES> is standard. It's even very much
in line with the usage that Ed likes, i.e. the DOES> in the same word
as the CREATE of the word it modifies; it's easy to turn it into a
fully Ed-compliant usage of DOES>:

: define-disinst ( u table-xt disasm-xt "inst" -- )
here name string, ( u table-xt disasm-xt c-addr ) \ remember string
noname create 2, \ define anonymous word
execute lastxt swap ! \ enter xt of defined word into table-xt
does> ( addr w -- )
\ disassemble instruction w at addr
2@ >r ( addr w disasm-xt R: c-addr )
execute ( R: c-addr ) \ disassemble operands
r> count type ; \ print name

: define-format ( disasm-xt table-xt -- )
\ define an instruction format that uses disasm-xt for
\ disassembling and enters the defined instructions into table
\ table-xt
create 2,
does> ( u "inst" -- )
\ defines an anonymous word for disassembling instruction inst,
\ and enters it as u-th entry into table-xt
2@ swap define-disinst ;

Anton Ertl

unread,
Dec 8, 2011, 7:37:33 AM12/8/11
to
1) The Hayes tests.

2) <http://www.complang.tuwien.ac.at/forth/struct.fs> contains this
code:

: dofield ( -- )
does> ( name execution: addr1 -- addr2 )
@ + ;

: dozerofield ( -- )
immediate
does> ( name execution: -- )
drop ;

: create-field ( align1 offset1 align size "name" -- align2 offset2 )
create swap rot over nalign dup , ( align1 size align offset )
rot + >r nalign r> ;

: field ( align1 offset1 align size "name" -- align2 offset2 )
\ name execution: addr1 -- addr2
2 pick >r \ this uglyness is just for optimizing with dozerofield
create-field
r> if \ offset<>0
dofield
else
dozerofield
then ;

BruceMcF

unread,
Dec 8, 2011, 10:48:32 AM12/8/11
to
On Dec 8, 6:02 am, Gerry Jackson <ge...@jackson9000.fsnet.co.uk>
wrote:
> On 07/12/2011 22:21, Ed wrote:
>> One DOES>  in a definer is plentiful and sufficient.  Anything
>> more is mind-boggling.

> That may be true. But the GForth manual gives a real-life use for two
> DOES>'s in one word, see section 5.9.8.3, but that usage does
> appear to be non-standard Forth.

Further, the notion that two successive DOES> have to be two
successive DOES> in one word follows from the unwillingness to
recognize that CREATE DOES> from when it was first proposed was never
limited to being used within one word, so two successive DOES> can be
a more common action for a defined structure and then an alternate,
less common action that applies to the same defined structure:
: make-type1 CREATE build-thing DOES> foo1 ;
: does-type2 DOES> foo2 ;

make-type1 Something2 does-type2

... is an idiom that was in use before the informal Forth83 standard
from which Ed derives his claim that:
: <name> ... CREATE ... DOES> ... ;
... is the "correct syntax" for CREATE DOES>


Albert van der Horst

unread,
Dec 10, 2011, 1:05:12 PM12/10/11
to
In article <a958a95c-0621-49bb...@y18g2000yqy.googlegroups.com>,
BruceMcF <agi...@netscape.net> wrote:
>On Dec 7, 7:16=A0pm, "Ed" <nos...@invalid.com> wrote:
>> In fact *all* the Hayes DOES> tests are weird. =A0There is not a single
>> test which tests =A0 : x =A0<create> ... DOES> =A0... =A0;
>
>But if the most recent definition was made by CREATE, and it has its
>behavior correctly modified by DOES> when the word containing DOES> is
>executed, what *difference* does it make if the CREATE was executed in
>the same definition, in a different definition, or directly executed
>in the command interpreter?
>
>There is absolutely no reason why factoring ought to break the correct
>execution behavior of DOES>

Yes there is. The semicolon that ends a definition is not the
same semicolon that ends a DOES> part.
A more sensible syntax would be
: test CREATE ... DOES> ... ;D ... ;

Now it is reasonable to say that factoring should not
break this code as long as the part factored out
contains DOES> ... ;D as a whole.

That nobody wonders is a testimony to the weirdness of Forth.

Or (more specific):

Would you factor out `` DOES> 1 2 '' in
: test CREATE 5 4 DOES> 1 2 3 7 ;

: poo-money DOES> 1 2 ;
: test CREATE 5 4 poo-money 3 7 ;

Groetjes Albert

--
--
Albert van der Horst, UTRECHT,THE NETHERLANDS
Economic growth -- being exponential -- ultimately falters.
albert@spe&ar&c.xs4all.nl &=n http://home.hccnet.nl/a.w.m.van.der.horst

BruceMcF

unread,
Dec 10, 2011, 12:53:24 PM12/10/11
to
On Dec 10, 1:05 pm, Albert van der Horst <alb...@spenarnc.xs4all.nl>
wrote:
> In article <a958a95c-0621-49bb- b407-e6156a79a...@y18g2000yqy.googlegroups.com>, BruceMcF  <agil...@netscape.net> wrote:

> >There is absolutely no reason why factoring ought to break the correct
> >execution behavior of DOES>

> Yes there is. The semicolon that ends a definition is not the
> same semicolon that ends a DOES> part.
> A more sensible syntax would be
> : test CREATE ... DOES> ... ;D ... ;

What does the statement mean? "The semicolon that ends a definition is
not the same semicolon that ends a DOES> part." If that is a Forth94
DOES> then I don't follow how that section following ;D is ever
executed ... when DOES> is executed, it sets the most recently defined
word to perform the following compiles words, then exits the word in
which it is contained. If ;D is ...

: ;D POSTPONE ; POSTPONE [ ;

... then the stuff after ;D will compile, but there will be no way to
execute it.

Alex McDonald

unread,
Dec 10, 2011, 2:20:53 PM12/10/11
to
On Dec 10, 1:05 pm, Albert van der Horst <alb...@spenarnc.xs4all.nl>
wrote:
> In article <a958a95c-0621-49bb-b407-e6156a79a...@y18g2000yqy.googlegroups.com>,
>
> BruceMcF  <agil...@netscape.net> wrote:
> >On Dec 7, 7:16=A0pm, "Ed" <nos...@invalid.com> wrote:
> >> In fact *all* the Hayes DOES> tests are weird. =A0There is not a single
> >> test which tests =A0 : x =A0<create> ... DOES> =A0... =A0;
>
> >But if the most recent definition was made by CREATE, and it has its
> >behavior correctly modified by DOES> when the word containing DOES> is
> >executed, what *difference* does it make if the CREATE was executed in
> >the same definition, in a different definition, or directly executed
> >in the command interpreter?
>
> >There is absolutely no reason why factoring ought to break the correct
> >execution behavior of DOES>
>
> Yes there is. The semicolon that ends a definition is not the
> same semicolon that ends a DOES> part.
> A more sensible syntax would be
> : test CREATE ... DOES> ... ;D ... ;

That doesn't make sense... The part after ;D ? Is it part of TEST or
the DOES> ?

Anton Ertl

unread,
Dec 11, 2011, 6:19:16 AM12/11/11
to
Albert van der Horst <alb...@spenarnc.xs4all.nl> writes:
>The semicolon that ends a definition is not the
>same semicolon that ends a DOES> part.

But it is.

>A more sensible syntax would be
>: test CREATE ... DOES> ... ;D ... ;
>
>Now it is reasonable to say that factoring should not
>break this code as long as the part factored out
>contains DOES> ... ;D as a whole.
>
>That nobody wonders is a testimony to the weirdness of Forth.
>
>Or (more specific):
>
>Would you factor out `` DOES> 1 2 '' in
>: test CREATE 5 4 DOES> 1 2 3 7 ;
>
>: poo-money DOES> 1 2 ;
>: test CREATE 5 4 poo-money 3 7 ;

Now let's do it with your syntax:

: test CREATE 5 4 DOES> 1 2 3 7 ;D ;
: poo-money DOES> 1 2 ;
: test CREATE 5 4 poo-money 3 7 ;D ;

I guess that would not work, either, as you mentioned in your restriction

|as long as the part factored out
|contains DOES> ... ;D as a whole.

earlier.

So, yes, I Forth you cannot just take any subsequence of words and
turn it into a factor; that works for straight-line code without
locals and return-stack usage, but as soon as control flow, the return
stack, or locals come into play, the rules become more complicated.
And DOES> has to do with control flow, so it should not be surprising
that there are factoring restrictions when DOES> is involved.

Albert van der Horst

unread,
Dec 11, 2011, 4:25:11 PM12/11/11
to
In article <2011Dec1...@mips.complang.tuwien.ac.at>,
DOES> is not control flow. It is a warp out of compilation into
metacompilation time.

BruceMcF

unread,
Dec 11, 2011, 4:55:41 PM12/11/11
to
On Dec 11, 4:25 pm, Albert van der Horst <alb...@spenarnc.xs4all.nl>
wrote:
> DOES> is not control flow. It is a warp out of
> compilation into metacompilation time.

But at runtime of the word containing ``DOES>'', execution exits the
word containing ``DOES>'' at the point that ``DOES>'' occurs.
``DOES>'' could just as well be called ``;DOES>''.

: <name> ( x*i -- x*j )
CREATE <something1> ;DOES> <something2> ;

... means control flow leaves the <name> after <something1> and *also*
the word defined by CREATE takes on behavior <something2>.

: <name> ;DOES> <something> ;

... just means that <name> is a no-op at execution time *apart from*
resetting the behavior of the most recent definition to <do-
something>.

Discussion about what arbitrary factoring can be done is neither here
nor there. The fact is that the standard behavior of DOES> allows
factoring when there are certain types of overlap.

: <name1> CREATE <structure1> DOES> <something1> ;
: <name2> CREATE <structure1> DOES> <something2> ;
: <name3> CREATE <structure1> DOES> <something3> ;
: <name4> CREATE <structure1> DOES> <something4> ;
: <name5> CREATE <structure2> DOES> <something1> ;
: <name6> CREATE <structure2> DOES> <something2> ;
: <name7> CREATE <structure2> DOES> <something3> ;
: <name8> CREATE <structure2> DOES> <something4> ;
: <name9> CREATE <structure3> DOES> <something1> ;
: <name10> CREATE <structure3> DOES> <something2> ;
: <name11> CREATE <structure3> DOES> <something3> ;
: <name12> CREATE <structure3> DOES> <something4> ;

... can be factored as:

: <name1> CREATE <structure1> DOES> <something1> ;
: <name2> CREATE <structure2> DOES> <something1> ;
: <name3> CREATE <structure3> DOES> <something1> ;
: does-something2 DOES> <something2> ;
: does-something3 DOES> <something3> ;
: does-something4 DOES> <something4> ;

I've got some defining words that drop a counted string address on the
stack. I want to re-use them, but generate an ca,u string descriptor,
or copy the string onto the string stack, or it into a workspace
block. Just re-use them, then over-ride the DOES> behavior.

That works, and it works entirely independent of the question of what
*arbitrary* factorings are possible.

Anton Ertl

unread,
Dec 12, 2011, 7:35:33 AM12/12/11
to
Albert van der Horst <alb...@spenarnc.xs4all.nl> writes:
>>So, yes, [in] Forth you cannot just take any subsequence of words and
>>turn it into a factor; that works for straight-line code without
>>locals and return-stack usage, but as soon as control flow, the return
>>stack, or locals come into play, the rules become more complicated.
>>And DOES> has to do with control flow, so it should not be surprising
>>that there are factoring restrictions when DOES> is involved.
>
>DOES> is not control flow.

|6.1.1250 DOES>
|[...]
|Return control to the calling definition specified by nest-sys1.

It is. In particular, in the context of factoring.

Ed

unread,
Dec 12, 2011, 8:18:20 AM12/12/11
to
Coos Haak wrote:
> ...
> I have words in my assembler written by someone else before 1994 that are
> like this:
> : <name> CREATE .. DOES> .. CREATE .. DOES> .. ;
>
> To understand them took some time though. I have never had problem with
> their behavior.

Nesting defining words gets a mention in FD14/1

"This idea is not merely a clever trick; it is the basis of most object-oriented
Forth systems".





Ed

unread,
Dec 12, 2011, 8:20:54 AM12/12/11
to
Gerry Jackson wrote:
> ...
> The argument that the <create> and DOES> must exist in the same
> definition is undermined by the example code in section A.16.6.2.0715 of
> the ANS Forth standard.

They would have the same problem as others here - justifying *why*
they used it.

> DOES> cannot be used in a control structure. It makes sense to factor
> out the DOES> code if you want to do something like:
>
> : x DOES> one-behaviour ;
> : y DOES> another-behaviour ;
> : z CREATE ... if x else y then ;

Why not this

: x CREATE ... DOES> one-behaviour ;
: y CREATE ... DOES> another-behaviour ;

: z ... if x else y then ;

> > One DOES> in a definer is plentiful and sufficient. Anything
> > more is mind-boggling.
>
> ...
> Multiple DOES>'s could be used for a state machine where each DOES> puts
> the machine into the next state e.g.

Of the few state machines I've seen implemented in Forth, none have
employed multiple DOES>.

I note J.Noble's FSM (FD20/2) and yours employ a separated DOES> .
Seeing it used in a real application makes it a candidate for consideration.
However as Julian points out in the errata (FD20/3) ...

"I have separated the DOES> portion from the CREATE section of
the FSM compiler [...] following a suggestion from Morgenstern in
an old FD. ... It is not necessary to do this and the code Jerry sent
me keeps this in the FSM: definition..."

In FD14/1 Leo Morgenstern writing under the section 'Separating
CREATE and DOES> '.

"...This trick is not often used because it is not often useful..."

It begs the question whether a separated DOES> is ever useful.
Neither author seemed convinced.



Alex McDonald

unread,
Dec 12, 2011, 9:35:16 AM12/12/11
to
On Dec 12, 1:20 pm, "Ed" <nos...@invalid.com> wrote:
> Gerry Jackson wrote:
> > ...
> > The argument that the <create> and DOES> must exist in the same
> > definition is undermined by the example code in section A.16.6.2.0715 of
> > the ANS Forth standard.
>
> They would have the same problem as others here - justifying *why*
> they used it.
>
> > DOES> cannot be used in a control structure. It makes sense to factor
> > out the DOES> code if you want to do something like:
>
> > : x DOES> one-behaviour ;
> > : y DOES> another-behaviour ;
> > : z CREATE ... if x else y then ;
>
> Why not this
>
> : x CREATE ... DOES> one-behaviour ;
> : y CREATE ... DOES> another-behaviour ;
>
> : z ... if x else y then ;

Poor factoring.

>
> > > One DOES>  in a definer is plentiful and sufficient.  Anything
> > > more is mind-boggling.
>
> > ...
> > Multiple DOES>'s could be used for a state machine where each DOES> puts
> > the machine into the next state e.g.
>
> Of the few state machines I've seen implemented in Forth, none have
> employed multiple DOES>.
>
> I note J.Noble's FSM (FD20/2) and yours employ a separated DOES> .
> Seeing it used in a real application makes it a candidate for consideration.
> However as Julian points out in the errata (FD20/3) ...
>
>     "I have separated the DOES> portion from the CREATE section of
>     the FSM compiler [...] following a suggestion from Morgenstern in
>     an old FD. ...  It is not necessary to do this and the code Jerry sent
>     me keeps this in the FSM: definition..."
>
> In FD14/1 Leo Morgenstern writing under the section 'Separating
> CREATE and DOES> '.
>
>     "...This trick is not often used because it is not often useful..."
>
> It begs the question whether a separated DOES> is ever useful.
> Neither author seemed convinced.

This author is convinced it is useful, has used it extensively, and is
unimpressed by an argument from authority. And it doesn't change the
standard.

BruceMcF

unread,
Dec 12, 2011, 12:00:08 PM12/12/11
to
On Dec 12, 9:35 am, Alex McDonald <b...@rivadpm.com> wrote:
> This author is convinced it is useful, has used it extensively, and is
> unimpressed by an argument from authority. And it doesn't change the
> standard.

Quite. The burden of proof at this point in time is not on the utility
of being able to have DOES> and CREATE in separate definitions, but on
the utility of stripping out the present entitlement to do so.

Gerry Jackson

unread,
Dec 12, 2011, 3:26:30 PM12/12/11
to
On 12/12/2011 13:20, Ed wrote:
> Gerry Jackson wrote:
>> ...
>> The argument that the<create> and DOES> must exist in the same
>> definition is undermined by the example code in section A.16.6.2.0715 of
>> the ANS Forth standard.
>
> They would have the same problem as others here - justifying *why*
> they used it.
>

Why would they have to justify something that is permitted by the
standard? If you look at the code DO-VOCABULARY is used twice - once in
interpretation mode and the other in a compiled word. Justification is
obvious - factoring and not wishing to put interpreted code into a colon
definition. Anyway ISTM that it has already been justified by others.
Where's the problem?

>> DOES> cannot be used in a control structure. It makes sense to factor
>> out the DOES> code if you want to do something like:
>>
>> : x DOES> one-behaviour ;
>> : y DOES> another-behaviour ;
>> : z CREATE ... if x else y then ;
>
> Why not this
>
> : x CREATE ... DOES> one-behaviour ;
> : y CREATE ... DOES> another-behaviour ;
>
> : z ... if x else y then ;
>

If you want to needlessly replicate code, do that.

>>> One DOES> in a definer is plentiful and sufficient. Anything
>>> more is mind-boggling.
>>
>> ...
>> Multiple DOES>'s could be used for a state machine where each DOES> puts
>> the machine into the next state e.g.
>
> Of the few state machines I've seen implemented in Forth, none have
> employed multiple DOES>.

I haven't seen it either or used it myself, I just presented it as a
possibility.

>
> I note J.Noble's FSM (FD20/2) and yours employ a separated DOES> .
> Seeing it used in a real application makes it a candidate for consideration.
> However as Julian points out in the errata (FD20/3) ...
>
> "I have separated the DOES> portion from the CREATE section of
> the FSM compiler [...] following a suggestion from Morgenstern in
> an old FD. ... It is not necessary to do this and the code Jerry sent
> me keeps this in the FSM: definition..."
>
> In FD14/1 Leo Morgenstern writing under the section 'Separating
> CREATE and DOES> '.
>
> "...This trick is not often used because it is not often useful..."

It is not a trick and his opinion is just that, an opinion, and one that
is not shared by many others.

>
> It begs the question whether a separated DOES> is ever useful.
> Neither author seemed convinced.
>

So what.

--
Gerry
It is loading more messages.
0 new messages