Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Evaluatable in non-logical link inside BindLink clause #132

Closed
williampma opened this issue Jul 9, 2015 · 67 comments
Closed

Evaluatable in non-logical link inside BindLink clause #132

williampma opened this issue Jul 9, 2015 · 67 comments

Comments

@williampma
Copy link
Member

Just thought I would throw this out there. Doing cog-bind on the following craziness

(BindLink
    (VariableList (stv 1.000000 0.000000)
        (VariableNode "$A") ; [80]
        (VariableNode "$B") ; [92]
        (VariableNode "$C") ; [103]
    )
    (MemberLink (stv 1.000000 1.000000)
        (BindLink (stv 1.000000 0.000000)
            (VariableList (stv 1.000000 0.000000)
                (TypedVariableLink (stv 1.000000 0.000000)
                    (VariableNode "$A") ; [80]
                    (TypeNode "ConceptNode") ; [100]
                ) ; [101]
                (TypedVariableLink (stv 1.000000 0.000000)
                    (VariableNode "$B") ; [92]
                    (TypeNode "ConceptNode") ; [100]
                ) ; [102]
                (TypedVariableLink (stv 1.000000 0.000000)
                    (VariableNode "$C") ; [103]
                    (TypeNode "ConceptNode") ; [100]
                ) ; [104]
            ) ; [105]
            (AndLink (stv 1.000000 0.000000)
                (InheritanceLink (stv 1.000000 0.000000)
                    (VariableNode "$A") ; [80]
                    (VariableNode "$B") ; [92]
                ) ; [106]
                (InheritanceLink (stv 1.000000 0.000000)
                    (VariableNode "$B") ; [92]
                    (VariableNode "$C") ; [103]
                ) ; [107]
                (NotLink (stv 1.000000 0.000000)
                    (EqualLink (stv 1.000000 0.000000)
                        (VariableNode "$A") ; [80]
                        (VariableNode "$C") ; [103]
                    ) ; [108]
                ) ; [109]
            ) ; [110]
            (ExecutionOutputLink (stv 1.000000 0.000000)
                (GroundedSchemaNode "scm: pln-formula-simple-deduction") ; [111]
                (ListLink (stv 1.000000 0.000000)
                    (InheritanceLink (stv 1.000000 0.000000)
                        (VariableNode "$A") ; [80]
                        (VariableNode "$B") ; [92]
                    ) ; [106]
                    (InheritanceLink (stv 1.000000 0.000000)
                        (VariableNode "$B") ; [92]
                        (VariableNode "$C") ; [103]
                    ) ; [107]
                    (InheritanceLink (stv 1.000000 0.000000)
                        (VariableNode "$A") ; [80]
                        (VariableNode "$C") ; [103]
                    ) ; [112]
                ) ; [113]
            ) ; [114]
        ) ; [115]
        (ConceptNode "URE") ; [116]
    ) ; [118]
    (ListLink
        (VariableNode "$A") ; [80]
        (VariableNode "$B") ; [92]
        (VariableNode "$C") ; [103]
    )
)

gives me

ERROR: In procedure cog-bind: Unknown logical connective (MemberLink (stv 1.000000 1.000000)
...

I stumbled upon this when the BC algorithm tried to backward chain an untyped (VariableNode "$stuff") target (from modus ponens rule), which match to everything in the atomspace. Then since the variables inside the interior MemberLink are by current algorithmic definition "free", the MemberLink is added as a target as a "Variable Fullfillment Query", and then generate the above error when trying to ground it.

@jswiergo
Copy link
Member

jswiergo commented Jul 9, 2015

What I see in the code of pattern matcher you cannot use MemberLink as a top link in the query, because it is not evaluatable. I guess if you add EvaluationLink around that top link it should work. For me it sounds logical, though I have not got much experience with this type system.

@linas
Copy link
Member

linas commented Jul 9, 2015

We should ask @ngeiswei about this. When he simplified the format of the BindLink, I think that the top level link could be anything, in which case, its treated as a single clause.

In the good old days, it had to have the format

   AndLink
       clause 1
       clause 2
       ...
       clause N

Later on, the top could be AndLink, SequentialAndLink or ChoiceLink (and nothing else). Today, if it is not one of these three, but something else, then we could/should assume there is only one clause total to be satisfied. I guess that last part is not implemented/fully supported.

A short-term work-around is to wrap the MemberLink with an AndLink.

@williampma
Copy link
Member Author

What I found is that doing a simpler version

(cog-bind
  (BindLink 
   (VariableList (VariableNode "$A"))
   (MemberLink (InheritanceLink (VariableNode "$A") (ConceptNode "dog")))
   (ListLink (VariableNode "$A"))))

doesn't generate the error. So I think there's something special with the one at the top.

@williampma
Copy link
Member Author

Ah, so it's not just a MemberLink thing. In fact, it happens on any non-logical link with evaluatable inside. For example, the follow also generates the error.

(BindLink
    (VariableList (stv 1.000000 0.000000)
        (VariableNode "$A") ; [80]
        (VariableNode "$B") ; [92]
    )
    (ListLink (stv 1.000000 1.000000)
        (EqualLink (stv 1.000000 0.000000)
            (VariableNode "$A") ; [80]
            (VariableNode "$B") ; [103]
        ) ; [108]
        (ConceptNode "URE") ; [116]
    ) ; [118]
    (ListLink
        (VariableNode "$A") ; [80]
        (VariableNode "$B") ; [92]
    )
)

@williampma williampma changed the title MemberLink inside BindLink clause Evaluatable in non-logical link inside BindLink clause Jul 10, 2015
@ngeiswei
Copy link
Member

Looks like a PM bug to me (I have no more clue sorry).

@jswiergo
Copy link
Member

This is case 4) explained here:
https://github.com/opencog/atomspace/blob/master/opencog/query/PatternMatchEngine.cc#L1127-L1141
Seems hard to solve in general.

What we can do in your case is to introduce UniqueLink instead of

  (NotLink (stv 1.000000 0.000000)
      (EqualLink (stv 1.000000 0.000000)
          (VariableNode "$A") ; [80]
          (VariableNode "$C") ; [103]
        ) ; [108]
   )

This is what @linas has suggested how to deal with elimination rules:
#86 (comment)

Then there will be one less virtual atom in your first example (UniqueLink is supposed to be UnorderedLink). However what to do with ExecutionOutputLink remains open question. I think your intention is to match it without any execution. So it should be quoted somehow. Does the QuoteLink do the job? Do you have any other ideas?

@williampma
Copy link
Member Author

Hummm... I thought about the QuoteLink possibility, but it seems it is impossible to QuoteLink the evaluatable/virtual atom without ended up QuoteLink-ing the variables as well.

Maybe the way to do it is, any evaluatable not inside a logical link should just be matched as a normal atom?

@linas
Copy link
Member

linas commented Jul 13, 2015

William's last suggestion seems best: any evaluatable not inside a logical link should just be matched as a normal atom.

I would like to have @ngeiswei think about this, instead of saying "I don't know", because this is a general atomspace representation question, and not just a pattern-matcher question. Some link types are truth-valued (for example, the EqualLink) and it is not obvious what should happen when these are inside of non-logical links (e.g. the ListLink) For now, William's answer seems like the best answer, but its a bit confusing in general.

I have thought about, and wrote some preliminary code to make the above user-configurable, via callback, but left it partly-finished, pending use-cases that really do need more complex behavior.

@linas
Copy link
Member

linas commented Jul 13, 2015

Yes, it's exactly case 4.

There is a check here: https://github.com/opencog/atomspace/blob/master/opencog/query/PatternMatchEngine.cc#L1117 and, since EqualLink is "evaluatable", it is evaluated, and then, the containing ListLink or MemberLink causes the error to be thrown. The "evaluatable" flag is pre-compted, at the time that the bind link is defined. We could change this so that a term is "evaluatable" if and only if it is contained in another link that expects a truth value (i.e. a logical link). If it is not contained in this way, then it is not evaluatable.

The "is_evaluatable" check is based on these bits:

https://github.com/opencog/atomspace/blob/master/opencog/query/Pattern.h#L108-L111
https://github.com/opencog/atomspace/blob/master/opencog/query/Pattern.h#L121

These are computed here:
https://github.com/opencog/atomspace/blob/master/opencog/atoms/bind/PatternLink.cc#L433-L476

specifically:
https://github.com/opencog/atomspace/blob/master/opencog/atoms/bind/PatternLink.cc#L519
and L530 and line 539 ...

I had planed to do something similar for "exectuable terms" -- terms that could be executed, resulting in an atom -- but never got very far with that.

@linas
Copy link
Member

linas commented Jul 13, 2015

Anyway, @ngeiswei (and I guess Ben and Matt Ikle should weigh in, too ...) do you now see what the problem is? When pattern matching, some links can be evaluated to yield a truth value; others can be executed, yielding an atom; in either case, its not obvious what to do when these are not nested in a way that "makes sense".

It would be nice to have a good answer...

@ngeiswei
Copy link
Member

It's a complex issue and I haven't digested all the PM inner workings to spot THE problem..

Personally I would have approached the pattern matching problem the other way around, assuming a pattern is a predicate ([Atom] -> TV), and give some predicate construct (let's call it BelongLink) to allow to check whether an hypergraph belongs to the atomspace. For instance the problematic pattern above (William's compact version) would have been expressed as follows:

(BelongLink
    (ListLink (stv 1.000000 1.000000)
        (EqualLink (stv 1.000000 0.000000)
            (VariableNode "$A") ; [80]
            (VariableNode "$B") ; [103]
        ) ; [108]
        (ConceptNode "URE") ; [116]
)

So in the PM matcher lingo everything would be virtual if not told otherwise (BelongLink used for that).

Would that fundamentally fix the issue, probably not. It seems to me generally the problem is that not enough is explicitly specified, right?

I mean how do you match the following pattern

(EqualLink (VariableNode "$X") (VariableNode "$Y))

? Can you at all? Or can you match it via using SignatureLink?

@ngeiswei
Copy link
Member

If I'm right a whole clause is either virtual or not. I mean a part cannot be virtual while another part of it wouldn't, right? So what about using a VirtualLink on top of each virtual clause? Or symmetrically using a BelongLink on top of each non virtual ones?

@bgoertzel
Copy link
Contributor

Nil -- I'm not sure exactly what you mean by "virtual" here? Is it the
same as "quoted" (what we get via wrapping something in a QuoteLink)?

On Mon, Jul 13, 2015 at 5:48 AM, ngeiswei [email protected] wrote:

If I'm right a whole clause is either virtual or not. I mean a part cannot
be virtual while another part of it wouldn't, right? So what about using a
VirtualLink on top of each virtual clause? Or symmetrically using a
BelongLink on top of each non virtual ones?


Reply to this email directly or view it on GitHub
#132 (comment).

Ben Goertzel, PhD
http://goertzel.org

"The reasonable man adapts himself to the world: the unreasonable one
persists in trying to adapt the world to himself. Therefore all progress
depends on the unreasonable man." -- George Bernard Shaw

@williampma
Copy link
Member Author

I mean how do you match the following pattern

(EqualLink (VariableNode "$X") (VariableNode "$Y))

Couldn't it match to (EqualLink (VariableNode "$A") (VariableNode "$B")) given that $X and $Y are untyped?

@bgoertzel
Copy link
Contributor

yes I would think so...

On Mon, Jul 13, 2015 at 5:56 AM, William Ma [email protected]
wrote:

I mean how do you match the following pattern

(EqualLink (VariableNode "$X") (VariableNode "$Y))

Couldn't it match to (EqualLink (VariableNode "$A") (VariableNode "$B"))
given that $X and $Y are untyped?


Reply to this email directly or view it on GitHub
#132 (comment).

Ben Goertzel, PhD
http://goertzel.org

"The reasonable man adapts himself to the world: the unreasonable one
persists in trying to adapt the world to himself. Therefore all progress
depends on the unreasonable man." -- George Bernard Shaw

@ngeiswei
Copy link
Member

I just tried

scheme@(guile-user) [1]> (cog-bind (BindLink (EqualLink (VariableNode "X") (VariableNode "Y")) (ListLink (VariableNode "X") (VariableNode "Y"))))
$2 = (SetLink
)

so it doesn't match to anything, I think it assumes it's a virtual clause.

Ben a virtual clause is a clause that is a predicate rather than a pattern, so for instance

GreaterThan X Y

is a virtual clause, it doesn't try to find that in the atomspace instead it uses as a constraint to filter out matches (could be used here for instance if X and Y match number nodes, etc).

@ngeiswei
Copy link
Member

So "virtual" is almost the opposite of "quote". But QuoteLink is even stronger as is assumes the VariableNode are quoted as well (they only match themselves).

@ngeiswei
Copy link
Member

I suggest we re-implement the pattern matcher Nil's way, everything is predicate and turn the atomspace into a LambdaLink graveyard.

@ngeiswei
Copy link
Member

Or wrap virtual clauses into a VirtualLink...

@bgoertzel
Copy link
Contributor

I have thought about this a bit now...

Of course, related issues are encountered in LISP, and are dealt with there
via the quote and backquote mechanism, see e.g. discussion at

http://stackoverflow.com/questions/134887/when-to-use-quote-in-lisp

where they consider examples in which you want to evaluate only parts of
some complex expression...

What LISP does is to evaluate everything by default, and then you need to
override that with quotes and backquotes if you want to...

Here the question is whether we treat "logical links" as evaluable or not,
and then whether we treat links wrapping logical links as evaluable or not.

I'm not sure "any evaluatable not inside a logical link should just be
matched as a normal atom" can work in general, because sometimes it will be
complex to tell if an evaluatable is going to be inside a logical link or
not, after a whole expression is done being unraveled and evaluated.
Subtle and annoying issues of evaluation order could arise here. For
instance, suppose the logical link that is wrapped around the evaluatable
link, is not directly there in the pattern being matched but is produced by
some ExecutionOutputLink? Then what if this ExecutionOutputLink happens
to get executed after the evaluatable link is evaluated? Thing seem to
get pretty messy...

It would seem best to make things explicit. That is, we could say

-- the default for any link type except those on a certain list
(ExecutionOutputLink, GreaterThanLink, VariableNode, whatever) is to match
exactly rather than evaluate

-- if we want to evaluate a certain instance of one of these link types,
then we have to add some special marker, which would be the inverse of a
QuoteLink ... say a DoThisLink.. (in this case we might want to rename
QuoteLink as DontDoThisLink ;D) ...

This becomes a little awkward, because we then have two types of Atoms

  • those that are evaluated or executed by default when encountered by the PM
  • those that are literally matched by default when encountered by the PM

and when we want those of the first type to be literally matched we use
QuoteLink, and when we want those of the second type to be evaluated or
executed, we use DoThisLink

So in William's example

(BindLink
(VariableList (stv 1.000000 0.000000)
(VariableNode "$A") ; 80 ; [92]
)
(ListLink (stv 1.000000 1.000000)
(EqualLink (stv 1.000000 0.000000)
(VariableNode "$A") ; 80 ; [103]
) ; 108 ; [116]
) ; [118](ListLink
%28VariableNode) ; 80 ; [92]
)
)

it would just try to match the exact pattern given, i.e. to find $A, $B so that

(ListLink (stv 1.000000 1.000000)
    (EqualLink (stv 1.000000 0.000000)
        (VariableNode "$A") ; [80]
        (VariableNode "$B") ; [103]
    ) ; [108]
    (ConceptNode "URE") ; [116]
)

(where the EqualLink and ListLInk are not evaluated)

On the other hand, if we wanted the EqualLink to be evaluated then
we'd need to wrap it in a DoThisLink, and in that case the expression
would be matched by

ListLink

True

ConceptNode "URE"

if the pattern matcher found any $A, $B that were equal

-- Ben

On Sun, Jul 12, 2015 at 11:01 PM, William Ma [email protected]
wrote:

Hummm... I thought about the QuoteLink possibility, but it seems it is
impossible to QuoteLink the evaluatable/virtual atom without ended up
QuoteLink-ing the variables as well.

Maybe the way to do it is, any evaluatable not inside a logical link
should just be matched as a normal atom?


Reply to this email directly or view it on GitHub
#132 (comment).

Ben Goertzel, PhD
http://goertzel.org

"The reasonable man adapts himself to the world: the unreasonable one
persists in trying to adapt the world to himself. Therefore all progress
depends on the unreasonable man." -- George Bernard Shaw

@ngeiswei
Copy link
Member

We could make everything explicit, or assume that some atoms are evaluable (or evaluatable, not sure I understand the distinction). But I'm thinking in cases the link itself is a function (like EqualLink) maybe we could benefit from introducing a special FunQuoteLink to quote only the functional part of the link.

If executions were only relying on EvaluationLink or ExecutionOutputLink then you could always quote the predicate or schema, like if you'd want to match

ExecutionOutputLink
   GPN "plus"
   ListLink
       VariableNode "$X"
       VariableNode "$Y"

you could write the pattern

ExecutionOutputLink
   QuoteLink
       GPN "plus"
   ListLink
       VariableNode "$X"
       VariableNode "$Y"

to unambiguously tell that you don't want to execute it. But you can't do that for an EqualLink, thus a FunQuoteLink.

The other option is to use UnquoteLink (or DontDoThisLink as Ben coins it), but it seems a FunQuoteLink might allows to get more compact patterns in many practical cases.

@bgoertzel
Copy link
Contributor

How would FunQuoteLink handle logical links like EqualsLink etc. ?

On Mon, Jul 13, 2015 at 8:58 AM, ngeiswei [email protected] wrote:

We could make everything explicit, or assume that some atoms are evaluable
(or evaluatable, not sure I understand the distinction). But I'm thinking
in cases the link itself is a function (like EqualLink) maybe we could
benefit to introduce a special FunQuoteLink to quote only the functional
part of the link.

If executions were only relying on EvaluationLink or ExecutionOutputLink
then you could always quote the predicate or schema, like if you'd want to
match

ExecutionOutputLink
GPN "plus"
ListLink
VariableNode "$X"
VariableNode "$Y"

you could write the pattern

ExecutionOutputLink
QuoteLink
GPN "plus"
ListLink
VariableNode "$X"
VariableNode "$Y"

to unambiguously tell that you don't want to execute it. But you can't do
that for an EqualLink, thus a FunQuoteLink.

The other option is to use UnquoteLink (or DontDoThisLink as Ben coins
it), but it seems a FunQuoteLink might allows to get more compact patterns
in many practical cases.


Reply to this email directly or view it on GitHub
#132 (comment).

Ben Goertzel, PhD
http://goertzel.org

"The reasonable man adapts himself to the world: the unreasonable one
persists in trying to adapt the world to himself. Therefore all progress
depends on the unreasonable man." -- George Bernard Shaw

@jswiergo
Copy link
Member

When pattern matching, some links can be evaluated to yield a truth value; others can be executed, yielding an atom; in either case, its not obvious what to do when these are not nested in a way that "makes sense".

This is probably due to historical design, but what if every link that is evaluable/executable yield only atoms? Instead of truth value yield TrueValueNode or something like that? Maybe there is something I am not aware?
Then there would be no problem with nesting such atoms for example within ListLink. Sometimes types of atoms would not match but it may happen for many other types too and could report type error.

Having that, quoted evaluatable links would be matched without evaluation, unquoted would be matched after evaluation, replaced by the atom being a result of evaluation/execution.

Just throwing the idea up, not sure how poor it is :-)

@bgoertzel
Copy link
Contributor

On Mon, Jul 13, 2015 at 10:48 AM, Jacek Świergocki <[email protected]

wrote:

When pattern matching, some links can be evaluated to yield a truth value;
others can be executed, yielding an atom; in either case, its not obvious
what to do when these are not nested in a way that "makes sense".

This is probably due to historical design, but what if every link that is
evaluable/executable yield only atoms? Instead of truth value yield
TrueValueNode or something like that? Maybe there is something I am not
aware?

That would not be problematic so far as I know.... To consider that when
e.g. InheritanceLink is evaluated it yields a TruthValueNode...

Then there would be no problem with nesting such atoms for example within
ListLink. Sometimes types of atoms would not match but it may happen for
many other types too and could report type error.

Having that, quoted evaluatable links would be matched without evaluation,
unquoted would be matched after evaluation, replaced by the atom being a
result of evaluation/execution.

I am not sure that we want "match after evaluation" to be the default for
logical link types though.

Almost all the time, when e.g. InheritanceLink occurs in a pattern to be
matched, it is intended to be literally matched and not
matched-after-evaluation...

So it seems that the default for logical links should be match-literally ...

-- Ben

@ngeiswei
Copy link
Member

FunQuoteLink

Definition

Quote only the functional part of a functional link.

Example

Imagine you want to match the following without executing the EqualLink, but you still want to execute its arguments, you can't use a QuoteLink (cause you want to execute the arguments), but you can use a FunQuoteLink, to quote only the Equal part:

FunQuoteLink
   EqualLink
      ExecutionOutputLink
         GSN "ToBeRunAtPMTime-1"
      ExecutionOutputLink
         GSN "ToBeRunAtPMTime-2"

Is that clear?

@ngeiswei
Copy link
Member

GSN "ToBeRunAtPMTime-1" and GSN "ToBeRunAtPMTime-2" will still be executed at PM time. So it's really like writing

('equal arg1 arg2)

in LISP.

@bgoertzel
Copy link
Contributor

Yeah, now I get it... this seems a useful mechanism, sure... basically your
FunQuoteLink is like a LISP quote, and the current QuoteLink is like a LISP
'( ... )

I don't care what they're named, but both of these seem useful mechanisms...

Still I think the default for logical links should be literal matching, so
we still need QuoteLink, UnquoteLink (my DoThisLink) and
LocalQuoteLink/FunQuoteLink/whatever ...

Anyway I think the matter is conceptually clear now -- we just need to add
a bit more language mechanism to make it convenient to explicitly specify a
full spectrum of behaviors...

On Mon, Jul 13, 2015 at 11:01 AM, ngeiswei [email protected] wrote:

GSN "ToBeRunAtPMTime-1" and GSN "ToBeRunAtPMTime-2" will still be executed
at PM time. So it's really like writing

('equal arg1 arg2)

in LISP.


Reply to this email directly or view it on GitHub
#132 (comment).

Ben Goertzel, PhD
http://goertzel.org

"The reasonable man adapts himself to the world: the unreasonable one
persists in trying to adapt the world to himself. Therefore all progress
depends on the unreasonable man." -- George Bernard Shaw

@jswiergo
Copy link
Member

I have one more issue. It seems to me that we need to somehow distinguish logical links from the of top of the query that connect clauses to be matched from logical links that are inside part of the clause?

AndLink
   clause1
   OrLink
      clause2
      clause3

The former links should be evaluated by default, because we are not searching for them, the latter should be matched literally by defaut. How can we deal with that?

@jswiergo
Copy link
Member

Pattern matcher searches for each clause separately.

@bgoertzel
Copy link
Contributor

The OpenCog HK team has discussed this F2F with Cassio a bit earlier this
week...

The general conclusion was that, ugly as it is, introducing systematic use
of QuoteLink and UnquoteLink is probably the only way to go...

Of course, we could syntactically sugar this in the Scheme/python shells
somehow if we want to, but in terms of the Atomspace representation,
QuoteLink/UnquoteLink are basically right... and other options are going to
confuse people even more...

ben

On Tue, Jul 28, 2015 at 3:31 PM, ngeiswei [email protected] wrote:

I think using LocalQuoteLink should do the trick, for instance to match

UnquoteLink
VariableNode "$X"

you'd write

PMLink
VariableNode "$X"
LocalQuoteLink
UnquoteLink
VariableNode "$X"

an UnquoteLink can undo a QuoteLink but not a LocalQuoteLink cause it's on
the link type itself.

Now I wonder whether

PMLink
QuoteLink
VariableNode "$X"

would match things like

QuoteLink
ConceptNode "A"

or

VariableNode "$X"

BindLink would match the latter. If we use BindLink convention it means we
assume that a QuoteLink over a quoted expression quotes variables. I guess
that would be OK.

Introducing new links means indeed taking care of how to match them, but
it's still simpler than keeping track of what is evaluatable and what is
not.

Ultimately I don't mind having the quote being escaped by what is
evaluatable, as long as the behavior is well documented. But the more
complicated it gets the harder it is to well document anyway.


Reply to this email directly or view it on GitHub
#132 (comment).

Ben Goertzel, PhD
http://goertzel.org

"The reasonable man adapts himself to the world: the unreasonable one
persists in trying to adapt the world to himself. Therefore all progress
depends on the unreasonable man." -- George Bernard Shaw

@williampma
Copy link
Member Author

Humm... I wasn't aware of reaching a conclusion.

@bgoertzel
Copy link
Contributor

Hah .. OK, maybe only Cassio and I reached a conclusion in our own minds ;D

Our conclusion was just to copy LISP, which seems to be Nil's inclination
also...

What is your current preferred option?

ben

On Fri, Aug 14, 2015 at 5:13 PM, William Ma [email protected]
wrote:

Humm... I wasn't aware of a reaching a conclusion.


Reply to this email directly or view it on GitHub
#132 (comment).

Ben Goertzel, PhD
http://goertzel.org

"The reasonable man adapts himself to the world: the unreasonable one
persists in trying to adapt the world to himself. Therefore all progress
depends on the unreasonable man." -- George Bernard Shaw

@williampma
Copy link
Member Author

Does the LISP method allows you to evaluate part of the stuff inside quote? I recall Cassio mentioned UnquotedVariableNode, but what if you want to match UnquotedVariableNode literally (ie. you want to quote the UnquotedVariableNode)?

I don't think the system can have "unquote" anything since it is possible to lead to conflict. The solution will have to contain only "quoting".

Maybe Nil's LocalQuoteLink that only works on link would work (with QuoteLink works on everything), and no "unquote" anywhere.

As I said, since the pattern are auto-generate (as oppose to someone defining it by hand), if the atom is in the AtomSpace, it will be Pattern Matched eventually.

Suppose at one point we want to ground $A & $B in

EqualLink
  $A
  $B

without evaluating the EqualLink, then we added the following

LocalQuoteLink
  EqualLink
    $A
    $B

Now that the above is in the AtomSpace, we might at some step want to ground

LocalQuoteLink
  EqualLink
    $A
    $B

while matching the LocalQuoteLink as is, while grounding $A & $B, and not evaluating the EqualLink. Then do we add

LocalQuoteLink
   LocalQuoteLink
     EqualLink
       $A
       $B

what happens to the EqualLink now that the LocalQuoteLink wrapping it is not evaluated... is the EqualLink now executed?? I guess we should add

LocalQuoteLink
   LocalQuoteLink
      LocalQuoteLink
        EqualLink
          $A
          $B

so that the outer LocalQuoteLink quote the middle one, and the inner one quote the EqualLink. Now that this atom is in the AtomSpace, how to match it as is, while grounding $A, $B, so we add

LocalQuoteLink
 LocalQuoteLink
   LocalQuoteLink
    LocalQuoteLink
     LocalQuoteLink
      LocalQuoteLink
       LocalQuoteLink
        EqualLink
          $A
          $B

Maybe this is correct, and that's what needed. Kind of like doing printf("\\\\\\\\\\\\\\n") to print 6 \ in C.

@williampma
Copy link
Member Author

There might be strange confusing interaction between LocalQuoteLink & QuoteLink though.

Suppose again we have

  EqualLink
    $A
    $B

which we want to match literally without grounding, we do

QuoteLink
  EqualLink
    $A
    $B

Now that the above is in the AtomSpace, we want to match as is, so if we do

LocalQuoteLink
  QuoteLink
    EqualLink
      $A
      $B

we will ended up not evaluating the QuoteLink, and ended up making EqualLink evaluatable, and $A & $B ground-able.

So maybe the solution is to only have QuoteLink (no LocalQuoteLink) but makes it only work on its top atom, so

QuoteLink
  EqualLink
    QuoteLink
       $A
    QuoteLink
       $B

is needed to quote the original atom.

@bgoertzel
Copy link
Contributor

To be more exact about how LISP works, look at the Backquote specification

http://www.gnu.org/software/emacs/manual/html_node/elisp/Backquote.html

So I think the LISP backquote is like our QuoteLink, and the LISP comma
(embedded in a backquoted expression somewhere) is like our proposed (and
perhaps badly named) UnquoteLink ...

I'm not sure if we have use for some analogue of the LISP splicing operator
" ,@ " ...

LISP also has quasiquotes, which get complificated...

http://3e8.org/pub/scheme/doc/Quasiquotation%20in%20Lisp%20(Bawden).pdf

-- Ben

On Fri, Aug 14, 2015 at 6:16 PM, William Ma [email protected]
wrote:

There might be strange confusing interaction between LocalQuoteLink &
QuoteLink though.

Suppose again we have

EqualLink
$A
$B

which we want to match literally without grounding, we do

QuoteLink
EqualLink
$A
$B

Now that the above is in the AtomSpace, we want to match as is, so if we do

LocalQuoteLink
QuoteLink
EqualLink
$A
$B

we will ended up not evaluating the QuoteLink, and ended up making
EqualLink evaluatable, and $A & $B ground-able.

So maybe the solution is to only have QuoteLink (no LocalQuoteLink) but
makes it only work on its top atom, so

QuoteLink
EqualLink
QuoteLink
$A
QuoteLink
$B

is needed to quote the original atom.


Reply to this email directly or view it on GitHub
#132 (comment).

Ben Goertzel, PhD
http://goertzel.org

"The reasonable man adapts himself to the world: the unreasonable one
persists in trying to adapt the world to himself. Therefore all progress
depends on the unreasonable man." -- George Bernard Shaw

@williampma
Copy link
Member Author

Hummm.... so

`(1 2 (3 ,(+ 4 5)))
     ⇒ (1 2 (3 9))

but what if we actually want

`(1 2 (3 ,(+ 4 5)))
     ⇒ (1 2 (3 ,(+ 4 5)))

does LISP allow that?

@bgoertzel
Copy link
Contributor

it seems you can nest backquotes and commas

http://stackoverflow.com/questions/7549550/using-two-backquotes-and-commas-common-lisp

in the LISP spirit that "data is code" ...

On Fri, Aug 14, 2015 at 9:21 PM, William Ma [email protected]
wrote:

Hummm.... so

`(1 2 (3 ,(+ 4 5)))
⇒ (1 2 (3 9))

but what if we actually want

`(1 2 (3 ,(+ 4 5)))
⇒ (1 2 (3 ,(+ 4 5)))

does LISP allow that?


Reply to this email directly or view it on GitHub
#132 (comment).

Ben Goertzel, PhD
http://goertzel.org

"The reasonable man adapts himself to the world: the unreasonable one
persists in trying to adapt the world to himself. Therefore all progress
depends on the unreasonable man." -- George Bernard Shaw

@linas
Copy link
Member

linas commented Aug 16, 2015

When Ben talks about quote and unquote, I think he really means quasi-quote and unquote. You cannot wriggle your way out of a quote, but you can unquote your way out of a quasi-quote:
http://docs.racket-lang.org/reference/quasiquote.html
(this works in scheme just like in racket).
https://www.gnu.org/software/guile/manual/html_node/Expression-Syntax.html

Note that regular single-quote ' is quote while the back-tick ` is quasi-quote.

@linas
Copy link
Member

linas commented Aug 16, 2015

So, to answer William's question:

`(1 2 (3 ,(+ 4 5)))   ;;; back-tick is quasi-quote

yields (1 2 (3 9)), whereas

'(1 2 (3 ,(+ 4 5)))    ;;; regular tick is just quote.

yields (1 2 (3 (unquote (+ 4 5))))

@linas
Copy link
Member

linas commented Aug 16, 2015

This suggests the need for three link types: QuoteLink QuasiquoteLink and UnquoteLink -- the UnquoteLink can only work inside a QuasiquoteLink; it is powerless otherwise. Whether we shall someday need a UnquoteSplicingLink is unclear.

@bgoertzel
Copy link
Contributor

Linas,

What you're calling a quasiquote, I used to call a "backquote",

http://www.gnu.org/software/emacs/manual/html_node/elisp/Backquote.html

but yeah it's the same thing...

http://www.phyast.pitt.edu/~micheles/scheme/scheme8.html

So I think we agree, and Cassio concurred with this approach also....
Basically, this is in line with the maxim that every AI system inevitably
contains N different hacky versions of a LISP interpreter ;p ...

ben

On Sun, Aug 16, 2015 at 9:59 AM, Linas Vepštas [email protected]
wrote:

When Ben talks about quote and unquote, I think he really means
quasi-quote and unquote. You cannot wriggle your way out of a quote, but
you can unquote your way out of a quasi-quote:
http://docs.racket-lang.org/reference/quasiquote.html
(this works in scheme just like in racket).
https://www.gnu.org/software/guile/manual/html_node/Expression-Syntax.html

Note that regular single-quote ' is quote while the back-tick ` is
quasi-quote.


Reply to this email directly or view it on GitHub
#132 (comment).

Ben Goertzel, PhD
http://goertzel.org

"The reasonable man adapts himself to the world: the unreasonable one
persists in trying to adapt the world to himself. Therefore all progress
depends on the unreasonable man." -- George Bernard Shaw

@bgoertzel
Copy link
Contributor

I think only two link types are really required in our current case, though
-- Quote and Unquote

In Scheme (as you likely know), quote causes the S-expression quoted to be
constructed at compile time, whereas quasiquote causes the S-expression
to be constructed at run time

ftp://ftp.cs.utexas.edu/pub/garbage/cs345/schintro-v13/schintro_129.html

So if one isn't concerned about optimization of quoted expressions (via
compile-time construction), then one can ignore the quote/quasiquote
distinction and effectively just have quasiquote...

So my suggestion is to just have QuoteLink and UnquoteLink, where QuoteLink
behaves like Scheme quasiquote and UnquoteLink behaves like Scheme unquote

I think this is what Nil was suggesting a while ago in this thread... and
what Cassio suggested in our F2F at the HK office last week...

-- Ben

On Sun, Aug 16, 2015 at 10:06 AM, Linas Vepštas [email protected]
wrote:

This suggests the need for three link types: QuoteLink QuasiquoteLink and
UnquoteLink -- the UnquoteLink can only work inside a QuasiquoteLink; it is
powerless otherwise. Whether we shall someday need a UnquoteSplicingLink is
unclear.


Reply to this email directly or view it on GitHub
#132 (comment).

Ben Goertzel, PhD
http://goertzel.org

"The reasonable man adapts himself to the world: the unreasonable one
persists in trying to adapt the world to himself. Therefore all progress
depends on the unreasonable man." -- George Bernard Shaw

@ngeiswei
Copy link
Member

Guys, we've got an AbsentLink for when a pattern in not in the atomspace, let's use a PresentLink for when a pattern is in the AtomSpace. You say "it's verbose", I say "fuck that!" :-D. You can always create helper functions to workaround the verbosity, but you cannot hand to the user such a complex badly specified behavior. In its last email Linas said

"The meta-problem with the pattern matcher is that it is not obvious
(to newcomers) that some clauses are being used for matching, and
other clauses are being used for their TV only."

I think he has a point. What isn't good to a newcomers isn't good to us.

Yes most patterns will be populated with PresentLink, on the other hand the use for QuoteLink and the like will drop considerably (only when you need to match variables inside pattern, or maybe I'm missing something).

@bgoertzel
Copy link
Contributor

If we wanted to use PresentLink, we would just have to wrap it around the
outer BindLink passed to the PM, right? Then AbsentLink would be used to
override this default PresentLink..

So most patterns would not be populated with PresentLink, but would simply
be wrapped with PresentLink -- if we wanted to go that way...

On Tue, Aug 18, 2015 at 6:53 PM, ngeiswei [email protected] wrote:

Guys, we've got an AbsentLink for when a pattern in not in the atomspace,
let's use a PresentLink for when a pattern is in the AtomSpace. You say
"it's verbose", I say "fuck that!" :-D. You can always create helper
functions to workaround the verbosity, but you cannot hand to the user such
a complex badly specified behavior. In its last email Linas said

"The meta-problem with the pattern matcher is that it is not obvious
(to newcomers) that some clauses are being used for matching, and
other clauses are being used for their TV only."

I think he has a point. What isn't good to a newcomers isn't good to us.

Yes most patterns will be populated with PresentLink, on the other hand
the use for QuoteLink and the like will drop considerably (only when you
need to match variables inside pattern, or maybe I'm missing something).


Reply to this email directly or view it on GitHub
#132 (comment).

Ben Goertzel, PhD
http://goertzel.org

"The reasonable man adapts himself to the world: the unreasonable one
persists in trying to adapt the world to himself. Therefore all progress
depends on the unreasonable man." -- George Bernard Shaw

@ngeiswei
Copy link
Member

The (old) idea is to have everything evaluatable by default and use PresentLink to tell to search the a pattern. So for instance to define the deduction rule one would write

BindLink
   AndLink
      PresentLink
         ImplicationLink
            VariableNode "$X"
            VariableNode "$Y"
      PresentLink
         ImplicationLink
            VariableNode "$Y"
            VariableNode "$Z"
      NotLink
         EqualLink
            VariableNode "$X"
            VariableNode "$Z"
   ImplicationLink
      VariableNode "$X"
      VariableNode "$Z"

letting aside the formula on the implicand.

@ngeiswei
Copy link
Member

PresentLink is the BelongLink I introduced earlier, except the name is cooler, especially cause we've got an AbsentLink...

@bgoertzel
Copy link
Contributor

I guess I still don't see why we need to make that explicit

I mean when we have

ImplicationLink
Inheritance $X cat
Inheritance $X animal

do you want to say instead

ImplicationLink
PresentLink
Inheritance $X cat
PresentLink
Inheritance $X animal

?

On Tue, Aug 18, 2015 at 8:32 PM, ngeiswei [email protected] wrote:

PresentLink is the BelongLink I introduced earlier, except the name is
cooler, especially cause we've got an AbsentLink...


Reply to this email directly or view it on GitHub
#132 (comment).

Ben Goertzel, PhD
http://goertzel.org

"The reasonable man adapts himself to the world: the unreasonable one
persists in trying to adapt the world to himself. Therefore all progress
depends on the unreasonable man." -- George Bernard Shaw

@linas
Copy link
Member

linas commented Aug 18, 2015

On Tue, Aug 18, 2015 at 7:41 AM, bgoertzel [email protected] wrote:

I guess I still don't see why we need to make that explicit

I mean when we have

ImplicationLink
Inheritance $X cat
Inheritance $X animal

do you want to say instead

ImplicationLink
PresentLink
Inheritance $X cat
PresentLink
Inheritance $X animal

No, that would be wrong, or almost surely not what you meant. The
PresentLink evaluates to true or false: if the pattern matcher finds the
thing wrapped by PresentLink, then it replaces it by "true". This would be
wrong or weird inside an ImplicationLink. The only things you want above a
PresentLink would be AndLink, OrLink, NotLink, SequenctialAndLink, Choice
Link.

Sequential just means "you must evaluate in order"; pattern matching can
run unordered. ChoiceLink means "pick one and only one".

Anyway, I like PresentLink, it solves a different bit of queasiness I'm
getting with the behavior tree concept, that I need to fix today... We may
need unquote anyway, at some future date, but PresentLink really emphasizes
unambiguously that the marked component is being searched for, rather than
evaluated.

@linas
Copy link
Member

linas commented Aug 20, 2015

There is an easy work-around for PresentLink that already exists and is implemented. Its called ChoiceLink. I just tested it, and it works as expected. An arity-N ChoiceLink is true if and only if one (or more) of its outgoing st is in the atomspace (can be grounded in the atomspace). Thus, an arity-1 ChoiceLink is identical to an arity-1 PresentLink: its true if and only if the wrapped atom is present.

I defined PresentLink here: http://wiki.opencog.org/w/PresentLink and I defined it so that it requires all of its terms to be present. thus, PresentLink is like present-and, while ChoiceLink is like present-or. ChoiceLink works today!

Note some additional confusion: PrsentLink resembles SatisfactionLink, in that both are either true or false; but SatisfactionLink binds its variables, while PresentLink leaves them free.

I think the spec in http://wiki.opencog.org/w/PresentLink is sufficiently clear that it can be "easily" implemented. Seems like a good idea.

@ngeiswei
Copy link
Member

+1 for n-ary PresentLink.

Maybe having n-ary AbsentLink could be useful as well. In that case
NotLink AbsentLink wouldn't be equivalent to PresentLink except for
the unary case, but I don't think that would be a problem.

Also you say in the wiki page of PresentLink

"Unlike SatisfactionLink, a PresentLink cannot be used with the cog-bind function. "

Why is that?

Also, do you intend to make PresentLink mandatory? Which involves
re-populating all the existing BindLinks and GetLinks with
PresentLinks. Or to come up with a convention to avoid doing that?

@ngeiswei
Copy link
Member

I guess when PresentLink isn't used then the evaluatable per link conventions could be used... So for instance if one wants to search for the pattern EqualLink $X $Y it would be wrapped in a PresentLink.

@linas
Copy link
Member

linas commented Sep 13, 2015

I think this conversation has reached a conclusion; closing this as a bug report. If there are new issues, please open a new bug report.

BTW, PresentLink is now partly-implemented (in a rather narrow scope) via bug #218

@linas linas closed this as completed Sep 13, 2015
ngeiswei added a commit to ngeiswei/atomspace that referenced this issue Jul 21, 2020
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

5 participants