[Aeditor-talk] Regexp assertions

Mark msparshatt at yahoo.co.uk
Sat Dec 13 15:10:19 EST 2003


On Saturday 13 Dec 2003 2:15 pm, Simon Strandgaard wrote:
> On Sat, 2003-12-13 at 13:10, Mark wrote:
> > On Saturday 13 Dec 2003 10:38 am, Simon Strandgaard wrote:
> > > On Fri, 2003-12-12 at 21:46, Mark wrote:
> > > > I have a couple of questions
> > > >
> > > > I want to add some new classes for code assertions and closures,
> > > >
> > > > CodeBlock
> > > > 	CodeAssertion
> > > > 	Closure
> > >
> > > From my brief understanding of perl6, the only thing which are the
> > > difference on {closure} and <codeassertion>, are that codeassert
> > > ignores the result ?   Is that correct?
> >
> > Actually closures ignore the result.
>
> OK
>
> > > If this is the case, then I would join the 2 classes. Perhaps call the
> > > class 'InlineCode'... and have a boolean which indicates weather the
> > > result should be ignored or not.
> >
> > One problem is after rereading the docs I've found a third type of code
> > block, created using <{...}>. this executes the code and adds the result
> > to the regexp.
>
> ok
>
> > The types are
> > Closure 			{...}		Fails the match if the code raises an exception
> > Code assertion	<(...)>	Fails the match if the code returns false
> > Regexp code		<{...}>	Inserts the return value into the regexp
> >
> > There are two ways to handle these
> > 1: use a single class, storing the type of code block as a flag within
> > the class
> > 2: use a class for each type of code block
> >
> > Personally I'd prefer to go the second route. Most of the code would be
> > within the base class with each subclass overriding the call method to do
> > the right thing.
>
> problem with (2) are that you will repeat code _many_ times.
Not that much code needs to be repeated. The only methods that change are 
match and match_inspect. Everything else can just be put in the base class

> You will have to add 3 classes to AbstractSyntax module,
4 including the abstract base class

> extend every visitors with 3 #visit_xx methods.
really you just need 1 visit method. Or at least that's how it seems from 
looking at the visitor classes that are already defined.

>
> (1) is easiest to maintain and keep the big overview, thats what
> OO are all about.   I like (1).

Well OO-ness is in the eye of the beholder. IMHO giving objects that should 
have different behaviours different classes is more OO and helps 
maintainability by better encapsulating any changes.

Anyway this is the code that I'm proposing adding

        class CodeBlock < Expression
                def initialize(code)
                        @src = code
                        #fix me
                        #meed better way to create Proc object
                        @code = eval "proc {#{code}}"
                end
                attr_reader :code, :src
                def match(other)
                          raise "Calling match on abstract class"
                end
		def accept(visitor); visitor.visit_codeblock self end
		def ==(other); self.class == other.class and @src == other.src end
		def match_inspect
                          raise "Calling match_inspect on abstract class"
		end
        end
        class CodeAssertion < CodeBlock
                def match(other)
                        @code.call(other)
                end
		def match_inspect
                        "<(#@src)>"
		end
        end
        class Closure < CodeBlock
                def match(other)
                        begin
                                @code.call(other)
                                return true
                        rescue
                                return false;
                        end
                end
		def match_inspect
                        "{#@src}"
		end
        end
        class RegexpAssertion < CodeBlock
                def match(other)
                        regexp = @code.call()
                        #parse returned regexp
                        #match against other
                end
		def match_inspect
                        "<{#@src}>"
		end
        end
class AssignRegisterVisitor
        def visit_codeblock(i); end
end
class RegexPrettyPrintVisitor
	def visit_codeblock(i)
		format_leaf("Code block " + i.match_inspect)
	end
end

Best Regards

Mark Sparshatt



More information about the Aeditor-talk mailing list