From: Christophe Turle
Subject: Re: need list pattern-matching advice
Date: 
Message-ID: <41fabddc$0$21793$636a15ce@news.free.fr>
> You may have a look at CL-UNIFICATION (shameless plug) in
> common-lisp.net.  It seems it will do all you need and more.  Comments
> and bug reports welcome.

ok i have just install it on Clisp and make a test, it works.

Here is the cl-unification.asd i have written to make it works :

;;; -*- Mode: Lisp -*-

(defpackage #:cl-unification-system
    (:use #:cl #:asdf) )

(in-package #:cl-unification-system)


(defsystem :cl-unification
  :components ((:file "unification-package")
        (:file "variables"           :depends-on ("unification-package"))
        (:file "substitutions"       :depends-on ("unification-package"))
        (:file "lambda-list-parsing" :depends-on ("unification-package"))
        (:file "templates-hierarchy" :depends-on ("unification-package"))
        (:file "unifier"             :depends-on ("unification-package"))
        (:file "match-block"         :depends-on ("unification-package")) ))

;;; end of file -- cl-unification.asd --


I will read cl-unification and test it more deeply and send you my 
suggestions. In fact lots and lots example is great. Perhaps translating and 
adding examples from PAIP and on-lisp should be a good thing ?

I see that it follows the common pattern of unification with variables in 
the pattern. It is surely the good thing but i suspect extracting them 
should had benefits ...

A last thing, what do you put in place of ??? :

(unify '(img :src "picture.jpg" :width "400" :height "400" "really " (p 
"strange ?")) ???)

so

?x = img
?y = (:src "picture.jpg" :width "400" :height "400")
?z = ("really " (p "strange ?"))



Christophe Turle wrote:
> Hi all,
>
> Always doing list pattern matching with Lisp over and over, so i think 
> it's
> time Lisp do it for me ;-)
>
> I checked some pattern matcher but each time it appears that variables are
> mixed with the pattern. i find it difficult to read them and to extend the
> matcher.
>
> So the idea is to separate pattern from the references (here accessed via
> accessors)
> The goal was readability and declarativity.
>
> ;; used in stml an sexp html
> (def-type element
>   :pattern (list
>              (a symbol)
>              (spliced (serie (a keyword) (a symbol)))
>              (spliced (serie (or (a string) (a element)))) )
>   :accessors (element-tag     (the symbol)
>               element-avs     (first serie)
>               element-content (second serie) ))
>
> so after i can :
>
> ((lambda (x)
>    (print (element-tag x))
>    (print (element-avs x))
>    (print (element-content x)) )
>  '(img :src "picture.jpg" :width "400" :height "400" "really " (p "strange
> ?")) )
> =>
> img
> (:src "picture.jpg" :width "400" :height "400")
> ("really " (p "strange ?"))
>
>
> Similar functions for anonymous pattern matching should also be 
> implemented.
>
>
> I have started implementation :
>
> (make-accessor '(list toto (serie (a attr) (a value)) tata) '(the serie))
> => (lambda (x) (identity (nth 1 x)))
>
>
> any comments before going into the wall or re-inventing the wheel ;) ?
>
> Is there an implementation/theory somewhere with a similar idea ?


-- 
___________________________________________________________
Christophe Turle.
sava preview http://perso.wanadoo.fr/turle/lisp/sava.html
(format nil ···@~a.~a" 'c.turle 'wanadoo 'fr) 

From: Marco Antoniotti
Subject: Re: need list pattern-matching advice
Date: 
Message-ID: <ofSKd.8$fp1.16306@typhoon.nyu.edu>
Christophe Turle wrote:
>>You may have a look at CL-UNIFICATION (shameless plug) in
>>common-lisp.net.  It seems it will do all you need and more.  Comments
>>and bug reports welcome.
> 
> 
> ok i have just install it on Clisp and make a test, it works.
> 
> Here is the cl-unification.asd i have written to make it works :

The MK:DEFSYSTEM included works as well.

	...
> 
> I will read cl-unification and test it more deeply and send you my 
> suggestions. In fact lots and lots example is great. Perhaps translating and 
> adding examples from PAIP and on-lisp should be a good thing ?

Sure.

> I see that it follows the common pattern of unification with variables in 
> the pattern. It is surely the good thing but i suspect extracting them 
> should had benefits ...
> 
> A last thing, what do you put in place of ??? :
> 
> (unify '(img :src "picture.jpg" :width "400" :height "400" "really " (p 
> "strange ?")) ???)
> 
> so
> 
> ?x = img
> ?y = (:src "picture.jpg" :width "400" :height "400")
> ?z = ("really " (p "strange ?"))


Strictly speaking you cannot get that result as of now.  Unification 
does not work per se as a language recognizer.  However, you have the 
machinery and the entry points to build your own template.

I would create a new EXPRESSION-TEMPLATE subclass with syntax

	#T(* <template> <unification-variable> &optional <repetitions>)

or something like that.  In your case the resulting "pattern" would look 
like the following:

	#T(* (#T(keyword _) _) ?y 3)

You also need the "keyword" template, but that is just a simple special 
case of the symbol template.  (also note that in the above, you really 
have the symbol unify:_ )

Then build a match clause with a pattern like

(unify:match (#T(list ?x #T(* (#T(keyword ?_) ?_) ?y 3) &rest ?z)
               '(img :src "picture.jpg" :width "400" :height "400" 
"really " (p > "strange ?"))
     (print ?x)
     (print ?y)
     (print ?z))


The generic function UNIFY can be extended to accomodate the above.

I do not have much time these days to work on this, but I will welcome 
suggestions and code.   These "regexp-like" extensions are obviously 
very useful.


Cheers

--
marco
From: Christophe Turle
Subject: Re: need list pattern-matching advice
Date: 
Message-ID: <41fcce58$0$26227$626a14ce@news.free.fr>
>> ok i have just install it on Clisp and make a test, it works.
>>
>> Here is the cl-unification.asd i have written to make it works :
>
> The MK:DEFSYSTEM included works as well.

It didn't work for me ...
I have tried with a : (asdf:operate 'asdf:load-op :unification)
ok i have not tried long, quicker to write the corresponding asd file ;)

>> A last thing, what do you put in place of ??? :
>>
>> (unify '(img :src "picture.jpg" :width "400" :height "400" "really " (p 
>> "strange ?")) ???)
>>
>> so
>>
>> ?x = img
>> ?y = (:src "picture.jpg" :width "400" :height "400")
>> ?z = ("really " (p "strange ?"))
>
>
> Strictly speaking you cannot get that result as of now.  Unification does 
> not work per se as a language recognizer.  However, you have the machinery 
> and the entry points to build your own template.
>
> I would create a new EXPRESSION-TEMPLATE subclass with syntax
>
> #T(* <template> <unification-variable> &optional <repetitions>)
>
> or something like that.  In your case the resulting "pattern" would look 
> like the following:
>
> #T(* (#T(keyword _) _) ?y 3)
>
> You also need the "keyword" template, but that is just a simple special 
> case of the symbol template.  (also note that in the above, you really 
> have the symbol unify:_ )
>
> Then build a match clause with a pattern like
>
> (unify:match (#T(list ?x #T(* (#T(keyword ?_) ?_) ?y 3) &rest ?z)
>               '(img :src "picture.jpg" :width "400" :height "400" "really 
> " (p > "strange ?"))
>     (print ?x)
>     (print ?y)
>     (print ?z))

- instead of adding each time a special case like 'keyword', try to 
integrate types.
- 3 is a fixed value ...

> The generic function UNIFY can be extended to accomodate the above.
>
> I do not have much time these days to work on this, but I will welcome 
> suggestions and code.   These "regexp-like" extensions are obviously very 
> useful.

yes, match & create are the basis of very powerful declarative systems. As a 
first step, i will try to gather matching samples. I hope to show that 
classical pattern expressions need to separate patterns from bindings.

I don't like too much reader macros, it is less lispy and may cause trouble 
when meta-generated.

So now, i stop speaking and go lisping ;)


-- 
___________________________________________________________
Christophe Turle.
sava preview http://perso.wanadoo.fr/turle/lisp/sava.html
(format nil ···@~a.~a" 'c.turle 'wanadoo 'fr) 
From: Marco Antoniotti
Subject: Re: need list pattern-matching advice
Date: 
Message-ID: <A9xLd.10$fp1.18402@typhoon.nyu.edu>
Christophe Turle wrote:
>>>ok i have just install it on Clisp and make a test, it works.
>>>
>>>Here is the cl-unification.asd i have written to make it works :
>>
>>The MK:DEFSYSTEM included works as well.
> 
> 
> It didn't work for me ...
> I have tried with a : (asdf:operate 'asdf:load-op :unification)

Of course it does not work this way. :)

You need

	(mk:compile-system "unification")


> ok i have not tried long, quicker to write the corresponding asd file ;)
> 
> 
>>>A last thing, what do you put in place of ??? :
>>>
>>>(unify '(img :src "picture.jpg" :width "400" :height "400" "really " (p 
>>>"strange ?")) ???)
>>>
>>>so
>>>
>>>?x = img
>>>?y = (:src "picture.jpg" :width "400" :height "400")
>>>?z = ("really " (p "strange ?"))
>>
>>
>>Strictly speaking you cannot get that result as of now.  Unification does 
>>not work per se as a language recognizer.  However, you have the machinery 
>>and the entry points to build your own template.
>>
>>I would create a new EXPRESSION-TEMPLATE subclass with syntax
>>
>>#T(* <template> <unification-variable> &optional <repetitions>)
>>
>>or something like that.  In your case the resulting "pattern" would look 
>>like the following:
>>
>>#T(* (#T(keyword _) _) ?y 3)
>>
>>You also need the "keyword" template, but that is just a simple special 
>>case of the symbol template.  (also note that in the above, you really 
>>have the symbol unify:_ )
>>
>>Then build a match clause with a pattern like
>>
>>(unify:match (#T(list ?x #T(* (#T(keyword ?_) ?_) ?y 3) &rest ?z)
>>              '(img :src "picture.jpg" :width "400" :height "400" "really 
>>" (p > "strange ?"))
>>    (print ?x)
>>    (print ?y)
>>    (print ?z))
> 
> 
> - instead of adding each time a special case like 'keyword', try to 
> integrate types.
> - 3 is a fixed value ...

"keyword" is not a special case.  Keyword is a subtype of Symbol.  Types 
are pretty much integrated already.

The use of '3' above is to denote how many repetitions you need.  The 
alternative is to somehow build a parser into the system.  But I am not 
sure this would be simple.

>>The generic function UNIFY can be extended to accomodate the above.
>>
>>I do not have much time these days to work on this, but I will welcome 
>>suggestions and code.   These "regexp-like" extensions are obviously very 
>>useful.
> 
> 
> yes, match & create are the basis of very powerful declarative systems. As a 
> first step, i will try to gather matching samples. I hope to show that 
> classical pattern expressions need to separate patterns from bindings.

What you call "classical pattern expressions" are "language recognizer 
expressions" like Regexps and CFL recognizers.  They serve a somewhat 
different purpose.  The question I have is whether a hybrid language can 
be (more) useful.


> 
> I don't like too much reader macros, it is less lispy and may cause trouble 
> when meta-generated.

The #T reader macro expands into a MAKE-TEMPLATE.  You can use that in 
generated code.

Cheers
--
Marco
From: Joerg Hoehle
Subject: Re: need list pattern-matching advice
Date: 
Message-ID: <uekf8ed9m.fsf@users.sourceforge.net>
"Christophe Turle" <······@nospam.com> writes:
> I checked some pattern matcher but each time it appears that variables are 
> mixed with the pattern.
[later]
> I don't like too much reader macros, it is less lispy and may cause trouble 
> when meta-generated.

I believe you should not reject some library just because it provides
reader macros. These reader macros expand some more or less documented
function. You can use these instead.

> (def-type element
>   :pattern (list
>              (a symbol)
>              (spliced (serie (a keyword) (a symbol)))
>              (spliced (serie (or (a string) (a element)))) )
>   :accessors (element-tag     (the symbol)
>               element-avs     (first serie)
>               element-content (second serie) ))

BTW, I found your code snippet hard to read. What's (the symbol)? So
"hard to read" is very subjective. I'm pretty much used to ? and
??variables.  But you mostly want ?(var-name + type-based match) or
actually separate type-based match from variable names. Yet you need
to have a mapping from match parts to variables (or accessors), and I
had trouble understanding that mapping in your def-type example.

IIRC, Baker's META provides all of these (types via the @ reader
macro, IIRC). If you read his paper, you'll know what the reader
macros expand to.

To me, it looks like any pattern matching library that integrates
types would be suitable for your needs, but it should better integrate
backtracking -- because you had a circular definition in your example:
an X/HTML element may contain another X/HTML element.

Regards,
	Jorg Hohle Telekom/T-Systems Technology Center