Discussions related to Visual Prolog
Martin Meyer
VIP Member
Posts: 328
Joined: 14 Nov 2002 0:01

Problem with Scope Type Parameter

Unread post by Martin Meyer »

Hello Thomas,

using the Support pattern I came across a problem. Please have a look at my construct.

I start demonstrating the issue from the following code, which works out fine:

Code: Select all

interface myDomain{@Type}       domains         type = @Type.   end interface myDomain   %======   interface obj{@Type}       open myDomain{@Type}       predicates         doSomething : (type Val).       predicates         doSomethingElse : (type Val).   end interface obj   %---   class obj{@Type} : obj{@Type} end class obj   %---   implement obj{@Type}       supports objSite{@Type}     inherits objSupport{@Type}   clauses     new() :-         objSupport::new(This).   clauses     doSomething(Val) :-         stdIo::write(Val).   end implement obj   %======   interface objSite{@Type}       domains         dummy = @Type.       predicates from obj{@Type}         doSomething/1   end interface objSite   %======   interface objSupport{@Type}       domains         dummy = @Type.       predicates from obj{@Type}         doSomethingElse/1   end interface objSupport   %---   class objSupport{@Type} : objSupport{@Type}       constructors         new : (objSite{@Type}).   end class objSupport   %---   implement objSupport{@Type}       supports objSite{@Type}     delegate interface objSite{@Type} to site   facts     site : objSite{@Type}.   clauses     new(ObjSite) :-         site := ObjSite.   clauses     doSomethingElse(Val) :-         doSomething(Val).   end implement objSupport   %======   implement main   clauses     run() :-         Obj = obj::new(),         Obj:doSomething("I am a test").   end implement main   goal     console::runUtf8(main::run).
In the above code the dummy domains seem superfluous. When removing them the code becomes:

Code: Select all

interface myDomain{@Type}       domains         type = @Type.   end interface myDomain   %======   interface obj{@Type}       open myDomain{@Type}       predicates         doSomething : (type Val).       predicates         doSomethingElse : (type Val).   end interface obj   %---   class obj{@Type} : obj{@Type} end class obj   %---   implement obj{@Type}       supports objSite{@Type}     inherits objSupport{@Type}   clauses     new() :-         objSupport::new(This).   clauses     doSomething(Val) :-         stdIo::write(Val).   end implement obj   %======   interface objSite{@Type}       predicates from obj{@Type}         doSomething/1   end interface objSite   %======   interface objSupport{@Type}       predicates from obj{@Type}         doSomethingElse/1   end interface objSupport   %---   class objSupport{@Type} : objSupport{@Type}       constructors         new : (objSite{@Type}).   end class objSupport   %---   implement objSupport{@Type}       supports objSite{@Type}     delegate interface objSite{@Type} to site   facts     site : objSite{@Type}.   clauses     new(ObjSite) :-         site := ObjSite.   clauses     doSomethingElse(Val) :-         doSomething(Val).   end implement objSupport   %======   implement main   clauses     run() :-         Obj = obj::new(),         Obj:doSomething("I am a test").   end implement main   goal     console::runUtf8(main::run).
However on above code the compiler throws the (supposably incorrect) error c352 : Unused type parameter '@Type' at two places. To cure the errors I also remove the scope type parameters which are reported to be unused and come to the below version of the code:

Code: Select all

interface myDomain{@Type}       domains         type = @Type.   end interface myDomain   %======   interface obj{@Type}       open myDomain{@Type}       predicates         doSomething : (type Val).       predicates         doSomethingElse : (type Val).   end interface obj   %---   class obj{@Type} : obj{@Type} end class obj   %---   implement obj{@Type}       supports objSite     inherits objSupport   clauses     new() :-         objSupport::new(This).   clauses     doSomething(Val) :-         stdIo::write(Val).   end implement obj   %======   interface objSite       predicates from obj{_Type}         doSomething/1   end interface objSite   %======   interface objSupport       predicates from obj{_Type}         doSomethingElse/1   end interface objSupport   %---   class objSupport : objSupport       constructors         new : (objSite).   end class objSupport   %---   implement objSupport       supports objSite     delegate interface objSite to site   facts     site : objSite.   clauses     new(ObjSite) :-         site := ObjSite.   clauses     doSomethingElse(Val) :-         doSomething(Val).   end implement objSupport   %======   implement main   clauses     run() :-         Obj = obj::new(),         Obj:doSomething("I am a test").   end implement main   goal     console::runUtf8(main::run).
The above code compiles, but when running it, the call Obj:doSomething("I am a test") provokes an access violation.

Many regards
Martin
Peter Muraya
VIP Member
Posts: 147
Joined: 5 Dec 2012 7:29

Unread post by Peter Muraya »

Hi Martin,
Thomas will hopefully address the access violation issue, but I have never understood why the compiler should complain that the parameter @Type is not used in the following construct -- which is why you needed to add the dummy line.

Code: Select all

  interface objSupport{@Type}       predicates from obj{@Type}         doSomethingElse/1   end interface objSupport
My intuition tells me that it is indeed used in the predicates from clause. Is it not?
Mutall Data Management Technical Support
User avatar
Thomas Linder Puls
VIP Member
Posts: 1398
Joined: 28 Feb 2000 0:01

Unread post by Thomas Linder Puls »

The compiler have a bug for "predicates from" code like this:

Code: Select all

interface objSupport{@Type}       predicates from obj{@Type}         doSomethingElse/1   end interface objSupport
You can circumvent the bug by making sure that you use the same formal type parameter name in all levels.

I.e. if the obj interface uses a type parameter named @Type, then the "predicates from" must also use @Type and hence the parameter in objSupport will have to be called @Type.

And then you will have to introduce dummy usages to prevent the unused type parameter error. All in all you end up with your original code.

We have noted this as compiler bugs, but I cannot say when it will be solved.
Regards Thomas Linder Puls
PDC
Martin Meyer
VIP Member
Posts: 328
Joined: 14 Nov 2002 0:01

Unread post by Martin Meyer »

Hi Peter,

I also have not understood why the compiler should complain on that construct, and I suspect compiler's complain is incorrect. I suppose, the compiler fails to see the usage of @Type, because the usage is indirect via domain type in myDomain{@Type}. And that's the relevant issue.

That the access violation happens, is not of much relevance, because it's happening on quite strange code. I guess it occurs, because stdIo::write unexpectedly cannot determine the type of it's argument when it internally wants to convert it to a string.

Best regards
Martin
Martin Meyer
VIP Member
Posts: 328
Joined: 14 Nov 2002 0:01

Unread post by Martin Meyer »

Thanx Thomas for the info!

I was filing my answer to Peter before I've seen your message.

Best regards
Martin
User avatar
Thomas Linder Puls
VIP Member
Posts: 1398
Joined: 28 Feb 2000 0:01

Unread post by Thomas Linder Puls »

The compiler simply don't see the parameter in the "predicates from" and
  • therefore it may complain about no usage, and
  • therefore it (by accident) only works correctly if the actual parameter is a type parameter with same name as the corresponding formal parameter
Regards Thomas Linder Puls
PDC
Post Reply