See Taking the Code which you gave,
1)removing the (long,int) method, because in this method
the second parameter is the lowest in the hierarchy,
2)and adding a (float,int) method so as to generate ambiguity
after these changes if you follow the procedure,when comparing
you find only a single valid method
1)static void fn2(long b, long i)
as the second parameter searches in the first parameter's result
it has no other option,other than to take this result,
finally when it looks that if there is any other method which has the
second parameter lower than its own,it finds one with(double,int)
which generates an ambiguoty,heres a code with the changes
which gives the error,
-------------------------------------------------------------------------
Test.java:5: reference to fn2 is ambiguous, both method fn2(long,long) in
Test and method fn2(float,int) in Test match
final char c =12; fn2(c,c); //calls long int
-------------------------------------------------------------------------
An important thing to note is compiler even checks for any method defined
in your code which could generate ambiguoty For e.g.
if i just changed the (float,int) method to (double,int)method
than this will generate ambigouty with (float,float),although we have not
called any of these method.
but if anytime,in any case,if the parameter passed to this method is (12.2f,12),it will find the method (float,float),but the second parameter it finds lower in(double,int) so generates an ambigiuty,
Remember it just checks the methods for ambiguoty,whether you have called or not does not matter Here the code for that
give error at compilation
---------------------------------------------------------------------------
Test.java:5: reference to fn2 is ambiguous, both method fn2(float,float) in Test and method fn2(double,int) in Test match
final char c =12; fn2(c,c); //calls long int
^
1 error
---------------------------------------------------------------------------
if still any doubt i will be happy to clear it ,feel free to ask.
With Luck,
Anand