mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-27 10:03:11 +07:00
new overload resolution
This commit is contained in:
@@ -18,6 +18,7 @@ package com.intellij.psi;
|
||||
import com.intellij.openapi.diagnostic.Logger;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.pom.java.LanguageLevel;
|
||||
import com.intellij.psi.infos.MethodCandidateInfo;
|
||||
import com.intellij.psi.util.*;
|
||||
import com.intellij.util.Function;
|
||||
import com.sun.tools.javac.code.Kinds;
|
||||
@@ -163,6 +164,10 @@ public class PsiMethodReferenceUtil {
|
||||
|
||||
public static boolean isAcceptable(@Nullable final PsiMethodReferenceExpression methodReferenceExpression, PsiType left) {
|
||||
if (methodReferenceExpression == null) return false;
|
||||
final PsiElement argsList = PsiTreeUtil.getParentOfType(methodReferenceExpression, PsiExpressionList.class);
|
||||
if (MethodCandidateInfo.ourOverloadGuard.currentStack().contains(argsList)) {
|
||||
if (!methodReferenceExpression.isExact()) return true;
|
||||
}
|
||||
if (left instanceof PsiIntersectionType) {
|
||||
for (PsiType conjunct : ((PsiIntersectionType)left).getConjuncts()) {
|
||||
if (isAcceptable(methodReferenceExpression, conjunct)) return true;
|
||||
|
||||
@@ -18,8 +18,10 @@ package com.intellij.psi.infos;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.projectRoots.JavaSdkVersion;
|
||||
import com.intellij.openapi.projectRoots.JavaVersionService;
|
||||
import com.intellij.openapi.util.Computable;
|
||||
import com.intellij.openapi.util.Pair;
|
||||
import com.intellij.openapi.util.RecursionGuard;
|
||||
import com.intellij.openapi.util.RecursionManager;
|
||||
import com.intellij.openapi.util.registry.Registry;
|
||||
import com.intellij.pom.java.LanguageLevel;
|
||||
import com.intellij.psi.*;
|
||||
@@ -37,6 +39,7 @@ import java.util.Map;
|
||||
* @author ik, dsl
|
||||
*/
|
||||
public class MethodCandidateInfo extends CandidateInfo{
|
||||
public static final RecursionGuard ourOverloadGuard = RecursionManager.createGuard("overload.guard");
|
||||
public static final ThreadLocal<Map<PsiElement, Pair<PsiMethod, PsiSubstitutor>>> CURRENT_CANDIDATE = new ThreadLocal<Map<PsiElement, Pair<PsiMethod, PsiSubstitutor>>>();
|
||||
@ApplicabilityLevelConstant private int myApplicabilityLevel = 0;
|
||||
private final PsiElement myArgumentList;
|
||||
@@ -95,6 +98,20 @@ public class MethodCandidateInfo extends CandidateInfo{
|
||||
return myApplicabilityLevel;
|
||||
}
|
||||
|
||||
@ApplicabilityLevelConstant
|
||||
public int getPertinentApplicabilityLevel() {
|
||||
final PsiMethod method = getElement();
|
||||
if (method != null && method.hasTypeParameters() || myArgumentList == null || !PsiUtil.isLanguageLevel8OrHigher(myArgumentList)) {
|
||||
return getApplicabilityLevel();
|
||||
}
|
||||
return ourOverloadGuard.doPreventingRecursion(myArgumentList, false, new Computable<Integer>() {
|
||||
@Override
|
||||
public Integer compute() {
|
||||
return getApplicabilityLevelInner();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
public PsiSubstitutor getSiteSubstitutor() {
|
||||
return super.getSubstitutor();
|
||||
}
|
||||
|
||||
+4
-4
@@ -394,7 +394,7 @@ public class JavaMethodsConflictResolver implements PsiConflictResolver{
|
||||
for (Iterator<CandidateInfo> iterator = conflicts.iterator(); iterator.hasNext();) {
|
||||
ProgressManager.checkCanceled();
|
||||
CandidateInfo info = iterator.next();
|
||||
final int level = preferVarargs(info);
|
||||
final int level = preferVarargs((MethodCandidateInfo)info);
|
||||
if (level < maxApplicabilityLevel) {
|
||||
iterator.remove();
|
||||
}
|
||||
@@ -404,10 +404,10 @@ public class JavaMethodsConflictResolver implements PsiConflictResolver{
|
||||
return maxApplicabilityLevel;
|
||||
}
|
||||
|
||||
private static int preferVarargs(CandidateInfo info) {
|
||||
final int level = ((MethodCandidateInfo)info).getApplicabilityLevel();
|
||||
private static int preferVarargs(MethodCandidateInfo info) {
|
||||
final int level = info.getPertinentApplicabilityLevel();
|
||||
if (level == MethodCandidateInfo.ApplicabilityLevel.FIXED_ARITY) {
|
||||
final PsiMethod psiMethod = (PsiMethod)info.getElement();
|
||||
final PsiMethod psiMethod = info.getElement();
|
||||
if (psiMethod != null && psiMethod.isVarArgs() && JavaVersionService.getInstance().isAtLeast(psiMethod, JavaSdkVersion.JDK_1_7)) {
|
||||
return level + 1;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user