method signature specificity when using interface types

classic Classic list List threaded Threaded
5 messages Options
Reply | Threaded
Open this post in threaded view
|

method signature specificity when using interface types

Chris Greener-2
 
Friends, I'm seeing an issue with beanshell choosing the wrong method signatures when using interface types.
If the following java code below is called from beanshell it seems to incorrectly select the wrong display method signature. see output below
 
Another issue I'm seeing (not illustrated here) is when methods have ambiguous java signatures, beanshell executes the first method it finds.
This still happens even if the method call is explicitly typed from beanshell.
 
I'm trying to understand the extent of these issue and any workarounds. I'm maily concerned by the first issue as our interface implementations are broad and its somewhat difficult to detect when this happens. I first noticed this when application behaviour changed as method order in the compiled java source changed.
 
 
output from below
 
java IFoo
shell IFoo2    // this is incorrect - should have used method signature with IFoo
java IFoo2
shell IFoo2
 
 
 
// beanshell calling code
 
IFoo foo = Foo.createIFoo();  //should display IFoo

Foo.display( foo, "shell" );    //should display IFoo

IFoo2 foo2 = Foo.createIFoo2(); // should display IFoo2

Foo.display( foo2, "shell" );  // should display IFoo2

 
 
 
// java compiled code start here
 
public interface IFoo {
}
 

public interface IFoo2 {
}

public class Foo implements IFoo, IFoo2 {
    public String name = "Foo";

    public static IFoo createIFoo() {
        IFoo f = new Foo();
        Foo.display(f, "java");
        return f;
    }

    public static IFoo2 createIFoo2() {
        IFoo2 f = new Foo();
        Foo.display(f, "java");
        return f;
    }

    public static void display( IFoo f, String t ) {
        java.lang.System.out.println(t + " IFoo");
    }

    public static void display( IFoo2 f, String t ) {
        java.lang.System.out.println(t + " IFoo2");
    }
}

 

 

 

Reply | Threaded
Open this post in threaded view
|

method signature specificity when using interface types

Chris Greener
 
Friends, I'm seeing an issue with beanshell choosing the wrong method signatures when using interface types.
If the following java code below is called from beanshell it seems to incorrectly select the wrong display method signature. see output below
 
Another issue I'm seeing (not illustrated here) is when methods have ambiguous java signatures, beanshell executes the first method it finds.
This still happens even if the method call is explicitly typed from beanshell.
 
I'm trying to understand the extent of these issue and any workarounds. I'm mainly concerned by the first issue as our interface implementations are broad and its somewhat difficult to detect when this happens. I first noticed this when application behavior changed as method order in the compiled java source changed.
 
 
output from below
 
java IFoo
shell IFoo2    // this is incorrect - should have used method signature with IFoo
java IFoo2
shell IFoo2
 
 
 
// beanshell calling code
 
IFoo foo = Foo.createIFoo();  //should display IFoo

Foo.display( foo, "shell" );    //should display IFoo

IFoo2 foo2 = Foo.createIFoo2(); // should display IFoo2

Foo.display( foo2, "shell" );  // should display IFoo2

 
 
 
// java compiled code start here
 
public interface IFoo {
}
 

public interface IFoo2 {
}

public class Foo implements IFoo, IFoo2 {
    public String name = "Foo";

    public static IFoo createIFoo() {
        IFoo f = new Foo();
        Foo.display(f, "java");
        return f;
    }

    public static IFoo2 createIFoo2() {
        IFoo2 f = new Foo();
        Foo.display(f, "java"); <SCRIPT><!-- D(["mb","<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; return f;<br>&nbsp;&nbsp;&nbsp; }</p>\r\n<p>&nbsp;&nbsp;&nbsp; public static void display( IFoo f, String t ) {<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; java.lang.System.out.println(t + &quot; IFoo&quot;);<br>&nbsp;&nbsp;&nbsp; }</p>\r\n<p>&nbsp;&nbsp;&nbsp; public static void display( IFoo2 f, String t ) {<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; java.lang.System.out.println(t + &quot; IFoo2&quot;);<br>&nbsp;&nbsp;&nbsp; }<br>}<br></p>\r\n<p>&nbsp;</p>\r\n<p>&nbsp;</p>\r\n<p>&nbsp;</p></div>\r\n\r\n",0] ); D(["ce"]); D(["ms","136"] ); //--></SCRIPT>
        return f;
    }

    public static void display( IFoo f, String t ) {
        java.lang.System.out.println(t + " IFoo");
    }

    public static void display( IFoo2 f, String t ) {
        java.lang.System.out.println(t + " IFoo2");
    }
}

 

Reply | Threaded
Open this post in threaded view
|

Re: method signature specificity when using interface types

Alexey Zinger
Chris,

I don't think it's a reasonable expectation for BeanShell to resolve this
ambiguity.  The compiled code resolves this at compile time because the
compiler is aware of the reference type, which in this case resolves the
question.  However in terms of runtime, all BeanShell and any other
reflection-driven code has to go on is the object type itself, which does not
resolve this ambiguity since it implements both interfaces.  Seems like what
you're asking is for BeanShell to be somewhat strongly typed when possible or
at least be reference type aware, which may or may not gell with the mission
statement.  Certainly would be a heck of a tear-down.

--- Chris Greener <[hidden email]> wrote:

>  
> Friends, I'm seeing an issue with beanshell choosing the wrong method
> signatures when using interface types.
> If the following java code below is called from beanshell it seems to
> incorrectly select the wrong display method signature. see output below
>  
> Another issue I'm seeing (not illustrated here) is when methods have
> ambiguous java signatures, beanshell executes the first method it finds.
>
> This still happens even if the method call is explicitly typed from
> beanshell.
>  
> I'm trying to understand the extent of these issue and any workarounds.
> I'm mainly concerned by the first issue as our interface implementations
> are broad and its somewhat difficult to detect when this happens. I
> first noticed this when application behavior changed as method order in
> the compiled java source changed.
>  
>  
> output from below
>  
> java IFoo
> shell IFoo2    // this is incorrect - should have used method signature
> with IFoo
> java IFoo2
> shell IFoo2
>  
>  
>  
> // beanshell calling code
>  
> IFoo foo = Foo.createIFoo();  //should display IFoo
>
> Foo.display( foo, "shell" );    //should display IFoo
>
> IFoo2 foo2 = Foo.createIFoo2(); // should display IFoo2
>
> Foo.display( foo2, "shell" );  // should display IFoo2
>
>
>  
>  
>  
> // java compiled code start here
>  
> public interface IFoo {
> }
>  
>
> public interface IFoo2 {
> }
>
>
> public class Foo implements IFoo, IFoo2 {
>     public String name = "Foo";
>
>     public static IFoo createIFoo() {
>         IFoo f = new Foo();
>         Foo.display(f, "java");
>         return f;
>     }
>
>     public static IFoo2 createIFoo2() {
>         IFoo2 f = new Foo();
>         Foo.display(f, "java");
>         return f;
>     }
>
>     public static void display( IFoo f, String t ) {
>         java.lang.System.out.println(t + " IFoo");
>     }
>
>     public static void display( IFoo2 f, String t ) {
>         java.lang.System.out.println(t + " IFoo2");
>     }
> }
>
>
>  
>
>


Alexey
2001 Honda CBR600F4i (CCS)
1992 Kawasaki EX500
http://bsheet.sourceforge.net


               
__________________________________
Start your day with Yahoo! - Make it your home page!
http://www.yahoo.com/r/hs


-------------------------------------------------------
SF.Net email is sponsored by:
Tame your development challenges with Apache's Geronimo App Server. Download
it for free - -and be entered to win a 42" plasma tv or your very own
Sony(tm)PSP.  Click here to play: http://sourceforge.net/geronimo.php
_______________________________________________
Beanshell-users mailing list
[hidden email]
https://lists.sourceforge.net/lists/listinfo/beanshell-users
Reply | Threaded
Open this post in threaded view
|

RE: method signature specificity when using interface types

Chris Greener
In reply to this post by Chris Greener-2
Thanks for your response.
I agree that this could be the case for the second issue with ambiguous
method calls, as I would not expect beanshell to know.
However I would expect beanshell to see the ambiguity and report this
with a runtime error rather than selecting a method based on java code
method order. I would also expect beanshell to support the cast if
specified to resolve the ambiguity, however beanshell seems to ignore
the cast.

For the first issue I don't think there is an ambiguity as I'm typed to
the interface.
Even if we could not resolve this at runtime then how does beanshell
determine that the wrong method it selected was the better choice. This
doesn't make sense. I suspect there must be some beanshell error in how
it selects specificity through reflection.


Thanks again




-----Original Message-----
From: [hidden email]
[mailto:[hidden email]] On Behalf Of Alexey
Zinger
Sent: Friday, November 04, 2005 9:58 AM
To: [hidden email]
Subject: Re: [Beanshell-users] method signature specificity when using
interface types

Chris,

I don't think it's a reasonable expectation for BeanShell to resolve
this ambiguity.  The compiled code resolves this at compile time because
the compiler is aware of the reference type, which in this case resolves
the question.  However in terms of runtime, all BeanShell and any other
reflection-driven code has to go on is the object type itself, which
does not resolve this ambiguity since it implements both interfaces.
Seems like what you're asking is for BeanShell to be somewhat strongly
typed when possible or at least be reference type aware, which may or
may not gell with the mission statement.  Certainly would be a heck of a
tear-down.

--- Chris Greener <[hidden email]> wrote:

>  
> Friends, I'm seeing an issue with beanshell choosing the wrong method
> signatures when using interface types.
> If the following java code below is called from beanshell it seems to
> incorrectly select the wrong display method signature. see output
> below
>  
> Another issue I'm seeing (not illustrated here) is when methods have
> ambiguous java signatures, beanshell executes the first method it
finds.
>
> This still happens even if the method call is explicitly typed from
> beanshell.
>  
> I'm trying to understand the extent of these issue and any
workarounds.

> I'm mainly concerned by the first issue as our interface
> implementations are broad and its somewhat difficult to detect when
> this happens. I first noticed this when application behavior changed
> as method order in the compiled java source changed.
>  
>  
> output from below
>  
> java IFoo
> shell IFoo2    // this is incorrect - should have used method
signature

> with IFoo
> java IFoo2
> shell IFoo2
>  
>  
>  
> // beanshell calling code
>  
> IFoo foo = Foo.createIFoo();  //should display IFoo
>
> Foo.display( foo, "shell" );    //should display IFoo
>
> IFoo2 foo2 = Foo.createIFoo2(); // should display IFoo2
>
> Foo.display( foo2, "shell" );  // should display IFoo2
>
>
>  
>  
>  
> // java compiled code start here
>  
> public interface IFoo {
> }
>  
>
> public interface IFoo2 {
> }
>
>
> public class Foo implements IFoo, IFoo2 {
>     public String name = "Foo";
>
>     public static IFoo createIFoo() {
>         IFoo f = new Foo();
>         Foo.display(f, "java");
>         return f;
>     }
>
>     public static IFoo2 createIFoo2() {
>         IFoo2 f = new Foo();
>         Foo.display(f, "java");
>         return f;
>     }
>
>     public static void display( IFoo f, String t ) {
>         java.lang.System.out.println(t + " IFoo");
>     }
>
>     public static void display( IFoo2 f, String t ) {
>         java.lang.System.out.println(t + " IFoo2");
>     }
> }
>
>
>  
>
>


Alexey
2001 Honda CBR600F4i (CCS)
1992 Kawasaki EX500
http://bsheet.sourceforge.net


               
__________________________________
Start your day with Yahoo! - Make it your home page!
http://www.yahoo.com/r/hs


-------------------------------------------------------
SF.Net email is sponsored by:
Tame your development challenges with Apache's Geronimo App Server.
Download
it for free - -and be entered to win a 42" plasma tv or your very own
Sony(tm)PSP.  Click here to play: http://sourceforge.net/geronimo.php
_______________________________________________
Beanshell-users mailing list
[hidden email]
https://lists.sourceforge.net/lists/listinfo/beanshell-users



-------------------------------------------------------
SF.Net email is sponsored by:
Tame your development challenges with Apache's Geronimo App Server. Download
it for free - -and be entered to win a 42" plasma tv or your very own
Sony(tm)PSP.  Click here to play: http://sourceforge.net/geronimo.php
_______________________________________________
Beanshell-users mailing list
[hidden email]
https://lists.sourceforge.net/lists/listinfo/beanshell-users
Reply | Threaded
Open this post in threaded view
|

RE: method signature specificity when using interface types

Alexey Zinger
If I'm not mistaken, the two issues are essentially linked, unless Bean Shell
in fact keeps some loose type information whenever available per reference.
And basically it all comes down to types.  I just did a little poking around
(thanks Google) through the BeanShell site and it turns out the very first
section of the intro page (http://www.beanshell.org/manual/intro.html)
addresses the subject:

"...
Types are good. Without strongly type languages it would be very hard to write
large scale systems and make any assertions about their correctness before they
are run. But working with types imposes a burden on the developer. Types are
labels and labeling things can be tedious. It can be especially tedious during
certain kinds of development or special applications where it is flexibility
and not program structure that is paramount. There are times where simplicity
and ease of use is a more important criterion.
..."

I read it as "BeanShell does not keep typed references or expressions beyond
object reflection itself".  In your case, this basically is a prime example of
when it causes a problem.

As far as the question of throwing an exception when encountering ambiguous
methods, my guess is it stems from dealing with derivable primitives.  A long
time ago, I wrote a simple reflection interpreter for Java.  The biggest pain
in the butt was having to deal with matching method signatures with a value
that needed to be converted from one numerical type to another.  Example:

foo(double bar) { }

gets invoked:

float val = 8.7;
foo(val);

Fine, no prob, but what if I overload:

foo(float bar) { }

The natural expectation is that if foo(float) is available, I pick it, but if
not, I go for the next best thing -- foo(double).  That takes a bit of jumping
through hoops.  But that's with primitive numeric and their wrapper objects,
which are essentially dealt with through Number class and its subclasses.  But
what happens in cases such as yours where I have inheritence:

foo(Component bar) { }
foo(Container bar) { }

foo(new JPanel());

Neither method matches the object's exact type, so I guess the expectation is
to call the method closest in inheritence chain to the object, which would be
foo(Container).  But what if I have this:

foo(Component bar1, Container bar2) { }
foo(Container bar1, Component bar2) { }

foo(new JPanel(), new JPanel());

We're already in trouble, and we haven't even gotten to the whole mess with
multiple interface inheritence.  Well, what if we refer to the Java specs?
That's fine and good, except in these cases, I can bet my head the specs would
tell us to do the best we can using reference types, which we can't do because
we don't have them.  And then if ambiguity is not resolved, the compiler is
allowed to stop with an ambiguous method call error.  But the trouble is we
can't quite follow the same philosphy because we're not a compiler, but we're
doing this at runtime.  I can't speak for Pat, but I can only assume he's
gotten to this point and decided to not generate any kind of ambigous call
exception and just pick the first one.  Remember, casting makes no difference
to the reference.  It either passes or fails, but doesn't help in expression
evaluation and matching method signatures.  We may disagree on this philosophy,
but I suspect we gotta work with what we have and perhaps there can be an
ambiguous call exception raising introduced that can be explicitly turned on
through configuration, but not by default.

--- Chris Greener <[hidden email]> wrote:

> Thanks for your response.
> I agree that this could be the case for the second issue with ambiguous
> method calls, as I would not expect beanshell to know.
> However I would expect beanshell to see the ambiguity and report this
> with a runtime error rather than selecting a method based on java code
> method order. I would also expect beanshell to support the cast if
> specified to resolve the ambiguity, however beanshell seems to ignore
> the cast.
>
> For the first issue I don't think there is an ambiguity as I'm typed to
> the interface.
> Even if we could not resolve this at runtime then how does beanshell
> determine that the wrong method it selected was the better choice. This
> doesn't make sense. I suspect there must be some beanshell error in how
> it selects specificity through reflection.
>
>
> Thanks again
>
>
>
>
> -----Original Message-----
> From: [hidden email]
> [mailto:[hidden email]] On Behalf Of Alexey
> Zinger
> Sent: Friday, November 04, 2005 9:58 AM
> To: [hidden email]
> Subject: Re: [Beanshell-users] method signature specificity when using
> interface types
>
> Chris,
>
> I don't think it's a reasonable expectation for BeanShell to resolve
> this ambiguity.  The compiled code resolves this at compile time because
> the compiler is aware of the reference type, which in this case resolves
> the question.  However in terms of runtime, all BeanShell and any other
> reflection-driven code has to go on is the object type itself, which
> does not resolve this ambiguity since it implements both interfaces.
> Seems like what you're asking is for BeanShell to be somewhat strongly
> typed when possible or at least be reference type aware, which may or
> may not gell with the mission statement.  Certainly would be a heck of a
> tear-down.
>
> --- Chris Greener <[hidden email]> wrote:
>
> >  
> > Friends, I'm seeing an issue with beanshell choosing the wrong method
> > signatures when using interface types.
> > If the following java code below is called from beanshell it seems to
> > incorrectly select the wrong display method signature. see output
> > below
> >  
> > Another issue I'm seeing (not illustrated here) is when methods have
> > ambiguous java signatures, beanshell executes the first method it
> finds.
> >
> > This still happens even if the method call is explicitly typed from
> > beanshell.
> >  
> > I'm trying to understand the extent of these issue and any
> workarounds.
> > I'm mainly concerned by the first issue as our interface
> > implementations are broad and its somewhat difficult to detect when
> > this happens. I first noticed this when application behavior changed
> > as method order in the compiled java source changed.
> >  
> >  
> > output from below
> >  
> > java IFoo
> > shell IFoo2    // this is incorrect - should have used method
> signature
> > with IFoo
> > java IFoo2
> > shell IFoo2
> >  
> >  
> >  
> > // beanshell calling code
> >  
> > IFoo foo = Foo.createIFoo();  //should display IFoo
> >
> > Foo.display( foo, "shell" );    //should display IFoo
> >
> > IFoo2 foo2 = Foo.createIFoo2(); // should display IFoo2
> >
> > Foo.display( foo2, "shell" );  // should display IFoo2
> >
> >
> >  
> >  
> >  
> > // java compiled code start here
> >  
> > public interface IFoo {
> > }
> >  
> >
> > public interface IFoo2 {
> > }
> >
> >
> > public class Foo implements IFoo, IFoo2 {
> >     public String name = "Foo";
> >
> >     public static IFoo createIFoo() {
> >         IFoo f = new Foo();
> >         Foo.display(f, "java");
> >         return f;
> >     }
> >
> >     public static IFoo2 createIFoo2() {
> >         IFoo2 f = new Foo();
> >         Foo.display(f, "java");
> >         return f;
> >     }
> >
> >     public static void display( IFoo f, String t ) {
> >         java.lang.System.out.println(t + " IFoo");
> >     }
> >
> >     public static void display( IFoo2 f, String t ) {
> >         java.lang.System.out.println(t + " IFoo2");
> >     }
> > }
> >
> >
> >  
> >
> >
>
>
> Alexey
> 2001 Honda CBR600F4i (CCS)
> 1992 Kawasaki EX500
> http://bsheet.sourceforge.net
>
>
>
> __________________________________
> Start your day with Yahoo! - Make it your home page!
> http://www.yahoo.com/r/hs
>
>
> -------------------------------------------------------
> SF.Net email is sponsored by:
> Tame your development challenges with Apache's Geronimo App Server.
> Download
> it for free - -and be entered to win a 42" plasma tv or your very own
> Sony(tm)PSP.  Click here to play: http://sourceforge.net/geronimo.php
> _______________________________________________
> Beanshell-users mailing list
> [hidden email]
> https://lists.sourceforge.net/lists/listinfo/beanshell-users
>
>


Alexey
2001 Honda CBR600F4i (CCS)
1992 Kawasaki EX500
http://bsheet.sourceforge.net


               
__________________________________
Start your day with Yahoo! - Make it your home page!
http://www.yahoo.com/r/hs


-------------------------------------------------------
SF.Net email is sponsored by:
Tame your development challenges with Apache's Geronimo App Server. Download
it for free - -and be entered to win a 42" plasma tv or your very own
Sony(tm)PSP.  Click here to play: http://sourceforge.net/geronimo.php
_______________________________________________
Beanshell-users mailing list
[hidden email]
https://lists.sourceforge.net/lists/listinfo/beanshell-users