8410c5ef02
FossilOrigin-Name: fb6ce2ced2018bf5ce6c8b40db5b735ad66eb1bf4ece75c64375f4b62b363f81
119 lines
2.5 KiB
Forth
119 lines
2.5 KiB
Forth
This is a quick little thing to generate some statistics
|
|
from the RETRO image and VM, along with some introspection
|
|
to identify sigil handlers and word classes.
|
|
|
|
# Memory Use
|
|
|
|
First, memory. This is easy due to the defined constants
|
|
and queries provided by RETRO.
|
|
|
|
~~~
|
|
nl 'Memory: s:put nl nl
|
|
|
|
EOM '__Total_memory:_%n\n s:format s:put
|
|
FREE '__Free_memory:__%n\n s:format s:put
|
|
here '__Used_memory:__%n\n s:format s:put
|
|
~~~
|
|
|
|
# Dictionary
|
|
|
|
Next, some statistics on the dictionary. The header sizing
|
|
would need to be adjusted if you add or remove fields from
|
|
them.
|
|
|
|
The header contains fields for:
|
|
|
|
link to prior
|
|
address
|
|
pointer to class handler
|
|
null terminated string with the name
|
|
|
|
So the size is 4 cells (the three fields and null terminator)
|
|
plus the length of the name.
|
|
|
|
~~~
|
|
nl 'Dictionary: s:put nl nl
|
|
|
|
#0 [ d:name s:length #4 + + ] d:for-each
|
|
'__Headers_consume_%n\n s:format s:put
|
|
|
|
#0 [ d:name s:length + n:inc ] d:for-each
|
|
'__Names_consume_%n\n s:format s:put
|
|
~~~
|
|
|
|
Determine the number of words in the dictionary.
|
|
|
|
~~~
|
|
#0 [ drop n:inc ] d:for-each
|
|
'__%n_names_defined\n s:format s:put
|
|
~~~
|
|
|
|
Determine the average length of a word name.
|
|
|
|
~~~
|
|
#0 [ d:name s:length + ] d:for-each
|
|
#0 [ drop n:inc ] d:for-each
|
|
/ '__Average_name_length:_%n\n s:format s:put
|
|
~~~
|
|
|
|
And without the sigils...
|
|
|
|
~~~
|
|
#0 #0 [ d:name dup $: s:index/char n:inc + s:length + [ n:inc ] dip ] d:for-each swap /
|
|
'__Average_name_without_namespace:_%n\n s:format s:put
|
|
~~~
|
|
|
|
Longest name are...
|
|
|
|
~~~
|
|
#0 [ d:name s:length n:max ] d:for-each
|
|
'__Longest_names_are_%n_characters\n s:format s:put
|
|
~~~
|
|
|
|
# Identify Classes
|
|
|
|
Word classes are conventionally named as:
|
|
|
|
class:<name>
|
|
|
|
This prints the names of words matching them. It also demonstrates
|
|
constructing an array of the names, which can be adapted for other
|
|
purposes.
|
|
|
|
~~~
|
|
nl 'Classes: s:put nl nl
|
|
|
|
:identify-classes (-a)
|
|
here #0 ,
|
|
[ d:name dup 'class: s:contains/string?
|
|
&, &drop choose ] d:for-each
|
|
here over - n:dec over store ;
|
|
|
|
sp sp identify-classes [ s:put sp ] a:for-each nl
|
|
~~~
|
|
|
|
# Identify Sigils
|
|
|
|
Sigils are named as:
|
|
|
|
sigil:<character>
|
|
|
|
Unlike classes, this is not merely a convention, but an actual
|
|
requirement.
|
|
|
|
The process for obtaining an array of them and printing it is
|
|
the same as with the class handlers.
|
|
|
|
~~~
|
|
nl 'Sigils: s:put nl nl
|
|
|
|
:identify-sigils (-a)
|
|
here #0 ,
|
|
[ d:name dup 'sigil: s:contains/string?
|
|
&, &drop choose ] d:for-each
|
|
here over - n:dec over store ;
|
|
|
|
sp sp identify-sigils [ s:put sp ] a:for-each nl
|
|
|
|
nl
|
|
~~~
|