new overload resolution: reject explicitly typed lambda to be pertinent to applicability if any of its return expressions is not

This commit is contained in:
Anna Kozlova
2014-09-03 16:54:33 +04:00
parent 83c2d36544
commit 5fc5b2b300
4 changed files with 75 additions and 2 deletions
@@ -174,7 +174,6 @@ public class InferenceSession {
}
}
}
return true;
}
if (expr instanceof PsiLambdaExpression) {
if (!((PsiLambdaExpression)expr).hasFormalParameterTypes()) {
@@ -158,7 +158,8 @@ public class JavaMethodsConflictResolver implements PsiConflictResolver{
// A lambda expression or a method reference expression is potentially compatible with a type variable if the type variable is a type parameter of the candidate method.
final PsiClass paramClass = PsiUtil.resolveClassInType(paramType);
if (paramClass instanceof PsiTypeParameter && ((PsiTypeParameter)paramClass).getOwner() == method) continue;
if (!lambdaExpression.isAcceptable(((MethodCandidateInfo)conflict).getSubstitutor(false).substitute(paramType), lambdaExpression.hasFormalParameterTypes())) {
if (!lambdaExpression.isAcceptable(((MethodCandidateInfo)conflict).getSubstitutor(false).substitute(paramType),
InferenceSession.isPertinentToApplicability(lambdaExpression, method))) {
iterator.remove();
}
}
@@ -0,0 +1,17 @@
abstract class PertinentToApplicabilityOfExplicitlyTypedLambdaTest {
interface A {
B m(int a);
}
interface B {
int m(int b);
}
abstract void foo(A a);
abstract void foo(B b);
{
foo<error descr="Ambiguous method call: both 'PertinentToApplicabilityOfExplicitlyTypedLambdaTest.foo(A)' and 'PertinentToApplicabilityOfExplicitlyTypedLambdaTest.foo(B)' match">(x -> y -> 42)</error>;
}
}
@@ -0,0 +1,56 @@
/*
* Copyright 2000-2014 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.intellij.codeInsight.daemon.lambda;
import com.intellij.codeInsight.daemon.LightDaemonAnalyzerTestCase;
import com.intellij.codeInspection.LocalInspectionTool;
import com.intellij.codeInspection.unusedSymbol.UnusedSymbolLocalInspection;
import com.intellij.openapi.projectRoots.JavaSdkVersion;
import com.intellij.openapi.projectRoots.Sdk;
import com.intellij.testFramework.IdeaTestUtil;
import org.jetbrains.annotations.NonNls;
import org.jetbrains.annotations.NotNull;
public class OverloadResolutionTest extends LightDaemonAnalyzerTestCase {
@NonNls static final String BASE_PATH = "/codeInsight/daemonCodeAnalyzer/lambda/overloadResolution";
@NotNull
@Override
protected LocalInspectionTool[] configureLocalInspectionTools() {
return new LocalInspectionTool[]{
new UnusedSymbolLocalInspection(),
};
}
public void testPertinentToApplicabilityOfExplicitlyTypedLambda() throws Exception {
doTest();
}
private void doTest() {
doTest(true);
}
private void doTest(boolean warnings) {
IdeaTestUtil.setTestVersion(JavaSdkVersion.JDK_1_8, getModule(), getTestRootDisposable());
doTestNewInference(BASE_PATH + "/" + getTestName(false) + ".java", warnings, false);
}
@Override
protected Sdk getProjectJDK() {
return IdeaTestUtil.getMockJdk18();
}
}