* Introduction
-Factor supports various data types; atomic types include numbers of various kinds, strings of characters, and booleans. Compound data types include lists consisting of cons cells, vectors, and string buffers.
-
-Factor encourages programming in a functional style where new objects are returned and input parameters remain unmodified, but does not enforce this. No manifest type declarations are necessary, and all data types use exactly one slot each on the stack (unlike, say, FORTH).
-
-The internal representation of a Factor program is a linked list. Linked lists that are to be executed are referred to as ``quotations.'' The interpreter iterates the list, executing words, and pushing all other types of objects on the data stack. A word is a unique data type because it can be executed. Words come in two varieties: primitive and compound. Primitive words have an implementation coded in the host langauge (C or Java). Compound words are executed by invoking the interpreter recursively on their definition, which is also a linked list.
+Factor supports various data types; atomic types include numbers of
+various kinds, strings of characters, and booleans. Compound data types
+include lists consisting of cons cells, vectors, and string buffers.
+
+Factor encourages programming in a functional style where new objects
+are returned and input parameters remain unmodified, but does not
+enforce this. No manifest type declarations are necessary, and all data
+types use exactly one slot each on the stack (unlike, say, FORTH).
+
+The internal representation of a Factor program is a linked list. Linked
+lists that are to be executed are referred to as ``quotations.'' The
+interpreter iterates the list, executing words, and pushing all other
+types of objects on the data stack. A word is a unique data type because
+it can be executed. Words come in two varieties: primitive and compound.
+Primitive words have an implementation coded in the host language (C or
+Java). Compound words are executed by invoking the interpreter
+recursively on their definition, which is also a linked list.
* Control flow
-Control flow rests on two basic concepts: recursion, and branching. Words with compound definitions may refer to themselves, and there is exactly one primitive for performing conditional execution:
+Control flow rests on two basic concepts: recursion, and branching.
+Words with compound definitions may refer to themselves, and there is
+exactly one primitive for performing conditional execution:
1 10 < [ "10 is less than 1." print ] [ "whoa!" print ] ifte
==> 10 is less than 1.
5 [ 1 2 3 4 ] contains?
==> f
-It recurses down the list, until it reaches the end, in which case the outer ifte's 'false' branch is executed.
+It recurses down the list, until it reaches the end, in which case the
+outer ifte's 'false' branch is executed.
A quick overview of the words used here:
= ( x y -- ? )
-More complicated control flow constructs, such as loops and higher order functions, are usually built with the help of another primitive that simply executes a quotation at the top of the stack, removing it from the stack:
+More complicated control flow constructs, such as loops and higher order
+functions, are usually built with the help of another primitive that
+simply executes a quotation at the top of the stack, removing it from
+the stack:
[ 2 2 + . ] call
==> 4
-Here is an example of a word that applies a quotation to each element of a list. Note that it uses 'call' to execute the given quotation:
+Here is an example of a word that applies a quotation to each element of
+a list. Note that it uses 'call' to execute the given quotation:
: each ( list quotation -- )
#! Push each element of a proper list in turn, and apply a
>r ( x -- r:x ) - move top of data stack to/from 'extra hand'.
r> ( r:x -- x )
-Writing >r foo r> is analogous to [ foo ] in Joy. Occurrences of >r and r> must be balanced within a single word definition.
+Writing >r foo r> is analogous to [ foo ] in Joy. Occurrences of >r and
+r> must be balanced within a single word definition.
Linked list deconstruction:
+- telnetd should use multitasking\r
+- file-responder: Content-Length\r
+- HEAD request for file-responder\r
+ - nicer way to combine two paths\r
+ - icons for file responder\r
+- -1.1 3 ^ shouldn't give a complex number\r
+- don't show listener on certain commands\r
+- inferior hangs\r
+- plugin should not exit jEdit on fatal errors\r
+- IN: format base: work with all types of numbers\r
+- home key in the listener\r
+- wordpreview: don't show for string literals and comments\r
+- eliminate usage of long long\r
+- 64 bit support\r
- alist -vs- assoc terminology\r
-- some way to run httpd from command line\r
-- 'default responder' for when we go to root\r
- minimize stage2 initialization code, just move it to source files\r
+- clean up listener's action popups\r
+- jedit ==> jedit-word, jedit takes a file name\r
+- introduce ifte* and ?str-head/?str-tail where appropriate\r
+- cwd, cd, pwd, dir., pwd. words\r
+- namespace clone drops static var bindings\r
\r
+ bignums:\r
\r
\r
- add a socket timeout\r
- >lower, >upper for strings\r
-- telnetd should use multitasking\r
- accept multi-line input in listener\r
\r
+ docs:\r
\r
- logic\r
-- numbers game leaves extra on the stack\r
- examples of assoc usage\r
- unparse examples, and difference from prettyprint\r
- review doc formatting with latex2html\r
\r
- java factor: equal numbers have non-equal hashcodes!\r
- FactorLib.equal() not very good\r
-- IN: format base: work with all types of numbers\r
- investigate mandel.factor\r
\r
+ listener/plugin:\r
\r
-- inferior hangs\r
-- plugin should not exit jEdit on fatal errors\r
-- balance needs USE:\r
+- some way to not have previous definitions from a source file\r
+ clutter the namespace\r
+- use inferior.factor for everything not just listener\r
- fedit broken with listener\r
- maple-like: press enter at old commands to evaluate there\r
- input style after clicking link\r
\r
+ native:\r
\r
-- eliminate usage of long long\r
-- is the profiler using correct stack depth?\r
-- read1\r
- sbuf-hashcode\r
- vector-hashcode\r
- irc: stack underflow?\r
\r
+ misc:\r
\r
-- directory listings:\r
- - nicer way to combine two paths\r
- - icons for file responder\r
- - cwd, cd, pwd, dir., pwd. words\r
-- -1.1 3 ^ shouldn't give a complex number\r
+- some way to run httpd from command line\r
- don't rehash strings on every startup\r
- 'cascading' styles\r
-- jedit ==> jedit-word, jedit takes a file name\r
-- introduce ifte* and ?str-head/?str-tail where appropriate\r
-- namespace clone drops static var bindings\r
- ditch expand\r
- set-object-path\r
\r
+ httpd:\r
\r
+- 'default responder' for when we go to root\r
- quit responder breaks with multithreading\r
- wiki responder:\r
- port to native\r
- text styles\r
- if user clicks stop in browser, doesn't stop sending?\r
- log with date\r
-- return more header fields, like Content-Length, Last-Modified, and so on\r
-- HEAD request\r
-- basic authentication, using httpdAuth function from a config file\r
+ basic authentication, using httpdAuth function from a config file\r
+- file responder; last-modified field\r
equal. However, it will never be called this way.
With this out of the way, the implementation of judge-guess is an
-easy task to tackle. Using the words \texttt{inexact-guess}, \texttt{=},
-and \texttt{2dup}, we can write:
+easy task to tackle. Using the words \texttt{inexact-guess}, \texttt{2dup}, \textttt{2drop} and \texttt{=}, we can write:
\begin{alltt}
: judge-guess ( actual guess -{}- ? )
2dup = {[}
- correct f
+ 2drop correct f
{]} {[}
inexact-guess t
{]} ifte ;
\end{alltt}
-The word = is found in the \texttt{kernel} vocabulary, and the word 2dup is found in the \texttt{stack} vocabulary. Since \texttt{=}
-consumes both its parameters, we must first duplicate them with \texttt{2dup} so that later they can be passed
-to \texttt{correct} and \texttt{inexact-guess}. Try evaluating the following
+The word \texttt{=} is found in the \texttt{kernel} vocabulary, and the words \texttt{2dup} and \texttt{2drop} are found in the \texttt{stack} vocabulary. Since \texttt{=}
+consumes both its parameters, we must first duplicate them with \texttt{2dup}. The word \texttt{correct} does not need to do anything with these two numbers, so they are popped off the stack using \texttt{2drop}. Try evaluating the following
in the interpreter to see what's going on:
\begin{alltt}
clear 4 4 2dup = .s
\emph{\{ 4 4 t \}}
\end{alltt}
+
Test \texttt{judge-guess} with a few inputs:
\begin{alltt}
: judge-guess ( actual guess -- ? )
2dup = [
- correct f
+ 2drop correct f
] [
inexact-guess t
] ifte ;
<img class="nice-box" src="error.png">
-<p>A common error is a missing <code>USE:</code> declaration. The <b>Plugins</b>><b>Factor</b>><b>Use word at caret</b> command searches for the word at the caret in all vocabularies, and adds a <code>USE:</code> declaration for the vocabulary to the start of the source file -- in this case, <code>ifte</code> is found in the <code>combinators</code> vocabulary, and the parse error instantly goes away:</p>
+<p>A common error is a missing <code>USE:</code> declaration. The <b>Use word at caret</b> command searches for the word at the caret in all vocabularies, and adds a <code>USE:</code> declaration for the vocabulary to the start of the source file -- in this case, <code>ifte</code> is found in the <code>combinators</code> vocabulary, and the parse error instantly goes away:</p>
<img class="nice-box" src="word-use.png">
package factor.jedit;
-import factor.Cons;
+import factor.*;
import sidekick.*;
public class FactorParsedData extends SideKickParsedData
{
+ public FactorInterpreter interp;
public String in;
public Cons use;
- FactorParsedData(String fileName)
+ FactorParsedData(FactorInterpreter interp, String fileName)
{
super(fileName);
+ this.interp = interp;
}
}
plugin.factor.jedit.FactorPlugin.name=Factor
plugin.factor.jedit.FactorPlugin.version=0.65
plugin.factor.jedit.FactorPlugin.author=Slava Pestov
-plugin.factor.jedit.FactorPlugin.docs=/doc/plugin.html
+plugin.factor.jedit.FactorPlugin.docs=/doc/jedit/index.html
plugin.factor.jedit.FactorPlugin.depend.0=jedit 04.02.15.00
plugin.factor.jedit.FactorPlugin.depend.1=plugin errorlist.ErrorListPlugin 1.3.2
public class FactorSideKickParser extends SideKickParser
{
+ private WordPreview wordPreview;
+
//{{{ FactorSideKickParser constructor
public FactorSideKickParser()
{
super("factor");
+ wordPreview = new WordPreview();
+ } //}}}
+
+ //{{{ activate() method
+ /**
+ * This method is called when a buffer using this parser is selected
+ * in the specified view.
+ * @param editPane The edit pane
+ * @since SideKick 0.3.1
+ */
+ public void activate(EditPane editPane)
+ {
+ super.activate(editPane);
+ editPane.getTextArea().addCaretListener(wordPreview);
+ } //}}}
+
+ //{{{ deactivate() method
+ /**
+ * This method is called when a buffer using this parser is no longer
+ * selected in the specified view.
+ * @param editPane The edit pane
+ * @since SideKick 0.3.1
+ */
+ public void deactivate(EditPane editPane)
+ {
+ super.deactivate(editPane);
+ editPane.getTextArea().removeCaretListener(wordPreview);
} //}}}
//{{{ parse() method
public SideKickParsedData parse(Buffer buffer,
DefaultErrorSource errorSource)
{
- FactorParsedData d = new FactorParsedData(buffer.getPath());
-
FactorInterpreter interp = FactorPlugin.getInterpreter();
+ FactorParsedData d = new FactorParsedData(
+ interp,buffer.getPath());
String text;
--- /dev/null
+/* :folding=explicit:collapseFolds=1: */
+
+/*
+ * $Id$
+ *
+ * Copyright (C) 2004 Slava Pestov.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright notice,
+ * this list of conditions and the following disclaimer.
+ *
+ * 2. Redistributions in binary form must reproduce the above copyright notice,
+ * this list of conditions and the following disclaimer in the documentation
+ * and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES,
+ * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * DEVELOPERS AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
+ * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+ * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
+ * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+package factor.jedit;
+
+import factor.*;
+import java.util.*;
+import javax.swing.event.*;
+import org.gjt.sp.jedit.textarea.*;
+import org.gjt.sp.jedit.*;
+import org.gjt.sp.util.Log;
+import sidekick.*;
+
+public class WordPreview implements CaretListener
+{
+ public void caretUpdate(CaretEvent e)
+ {
+ showPreview((JEditTextArea)e.getSource());
+ }
+
+ private void showPreview(JEditTextArea textArea)
+ {
+ View view = textArea.getView();
+ String word = FactorPlugin.getWordAtCaret(textArea);
+ if(word == null)
+ return;
+ SideKickParsedData data = SideKickParsedData
+ .getParsedData(view);
+ if(data instanceof FactorParsedData)
+ {
+ FactorParsedData fdata = (FactorParsedData)data;
+ FactorWord w = fdata.interp
+ .searchVocabulary(fdata.use,word);
+ if(w != null)
+ {
+ view.getStatus().setMessageAndClear(
+ FactorWordRenderer.getWordHTMLString(
+ fdata.interp,w,true));
+ }
+ }
+ }
+}
void flip_zones()
{
- ZONE z = prior;
+ ZONE z = active;
active = prior;
prior = z;
}