Atomese Syntax Musings

From OpenCog
Jump to: navigation, search


WARNING: THIS IS JUST SOME EXPERIMENTAL MUSING, NOT A SUGGESTION FOR SOMETHING TO BE IMPLEMENTED NOW OR EVER...


Just as a quick syntactic experiment, I decided to transform a couple of Linas's "OpenCog behavior scripts" from

https://github.com/opencog/ros-behavior-scripting

into a less messy looking (to my eye) syntax...

This is in the spirit that the Pattern Matcher is becoming more and more like a programming language interpreter. We are using Scheme or python or Haskell with it, but we're using these languages to basically construct programs in an "Atomese" language, in effect...

So the experiment undertaken here is to simplify "Scheme for creating Atomese" into a simpler, pure-Atomese syntax (that could, as it happens, be translated into Scheme via some simple text processing..)

What I do is to introduce the following purely syntactic measures::

  • syntactically significant indenting, to avoid the need for so many parentheses
  • eliminate the Node, Link suffixes on Atom type names
  • Use 'Predicate as shorthand for (Evaluation Predicate), 'Schema as shorthand for (Execution Schema), Schema as shorthand for (ExecutionOutput Schema)
  • As an optional alternative to ( Variable "blah"), we can replace (Variable "$name") with simply $name ... That is, we can take the "$" at the start of the name to indicate that a Variable is being named
  • when an expression is prepended with "#oc" then this is an instruction to the interpreter to interpret that expression as the head of an OpenCog-syntax expression, that needs to be given special processing before ordinary interpretation begins
  • I thought about but didn't use in the below: Optionally use [ a, b, c] to denote (List a b c)  ; use {a, b, c} to denote (Set a b c).

Here are two examples, before and after the syntactic change:

BEFORE

(DefineLink
	(DefinedSchemaNode "New departures")
	(GetLink
		(AndLink
			; If someone was previously acked...
			(PresentLink (EvaluationLink (PredicateNode "acked face")
					(ListLink (VariableNode "$face-id"))))
			; But is no longer visible...
			(AbsentLink (EvaluationLink (PredicateNode "visible face")
					(ListLink (VariableNode "$face-id"))))
	)))
	
AFTER	

#oc Define
	DefinedSchema "new departures"
	Get
		And
			; If someone was previously acked...
			Present 
				'Predicate "acked face"
				$face-id
			;but is no longer visible
			Absent
				'Predicate "visible face"
				$face-id
	
	
BEFORE
	
(DefineLink
	(DefinedPredicateNode "Show expression")
	(LambdaLink
		(VariableList (VariableNode "$emo") (VariableNode "$expr"))
		(SequentialAndLink
			;; Record the time
			(TrueLink (DefinedSchemaNode "set expression timestamp"))
			;; Send it off to ROS to actually do it.
			(EvaluationLink (GroundedPredicateNode "py:do_emotion")
				(ListLink
					(VariableNode "$expr")
					(PutLink
						(DefinedSchemaNode "get random duration")
						(ListLink (VariableNode "$emo") (VariableNode "$expr")))
					(PutLink
						(DefinedSchemaNode "get random intensity")
						(ListLink (VariableNode "$emo") (VariableNode "$expr")))
			))
		)
	))
		
AFTER

#oc Define
	DefinedPredicate "Show expression"
	Lambda
		VariableList $emo $expr
		SequentialAnd
			;; Record the time
			True (DefinedSchema "set expression timestamp")
			;; Send it off to ROS to actually do it.
			'GroundedPredicate "py:do_emotion"
			List
				$expr
				Put
					DefinedSchema "get random duration"
					List $emo $expr
				Put
					DefinedSchema "get random intensity"
					List $emo  $expr
	


So in this particular approach, we could mix up Scheme functions and #oc functions in the same file, then run the OpenCog preprocessor on that file to turn it into Scheme, then interpret the Scheme. The Scheme interpreter would then relate any bugs to the Scheme file produced by the preprocessor.... So we get to have our own Atomese syntax for elegantly specifying Pattern Matcher programs, but without actually writing our own programming language...

An advantage of this sort of approach would be, potentially the same "Atomese" function definition could be used inside Scheme, python or Haskell... there would just be a preprocessor that would modify the Atomese syntax into the programming language of choice, where it could be used together with programming language specific code as needed...