IDEA-CR-13504 Lambda to method-reference: PsiVariable is accepted as it's necessary for StreamApiMigrationInspection;

StreamApiMigrationInspection.TerminalBlock simplified (myFrom/myTo did not actually improve performance, but added unnecessary logic)
This commit is contained in:
Tagir Valeev
2016-09-05 08:57:55 +07:00
parent 08fc28f682
commit 13d9f8d53a
3 changed files with 32 additions and 48 deletions
@@ -1,5 +1,5 @@
/*
* Copyright 2000-2012 JetBrains s.r.o.
* Copyright 2000-2016 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.
@@ -94,7 +94,7 @@ public class LambdaCanBeMethodReferenceInspection extends BaseJavaBatchLocalInsp
@Nullable
public static String convertToMethodReference(@Nullable final PsiElement body,
final PsiParameter[] parameters,
final PsiVariable[] parameters,
final PsiType functionalInterfaceType,
@Nullable PsiElement context) {
final PsiCallExpression toConvertCall = canBeMethodReferenceProblem(body, parameters, functionalInterfaceType, context);
@@ -104,14 +104,14 @@ public class LambdaCanBeMethodReferenceInspection extends BaseJavaBatchLocalInsp
@Nullable
public static PsiCallExpression canBeMethodReferenceProblem(@Nullable final PsiElement body,
final PsiParameter[] parameters,
final PsiVariable[] parameters,
final PsiType functionalInterfaceType) {
return canBeMethodReferenceProblem(body, parameters, functionalInterfaceType, null);
}
@Nullable
public static PsiCallExpression canBeMethodReferenceProblem(@Nullable final PsiElement body,
final PsiParameter[] parameters,
final PsiVariable[] parameters,
PsiType functionalInterfaceType,
@Nullable PsiElement context) {
final PsiCallExpression callExpression = extractMethodCallFromBlock(body);
@@ -181,7 +181,7 @@ public class LambdaCanBeMethodReferenceInspection extends BaseJavaBatchLocalInsp
return null;
}
private static boolean isSimpleCall(final PsiParameter[] parameters, PsiCallExpression callExpression, PsiMethod psiMethod) {
private static boolean isSimpleCall(final PsiVariable[] parameters, PsiCallExpression callExpression, PsiMethod psiMethod) {
final PsiExpressionList argumentList = callExpression.getArgumentList();
if (argumentList == null) {
return false;
@@ -240,7 +240,7 @@ public class LambdaCanBeMethodReferenceInspection extends BaseJavaBatchLocalInsp
return resolvesToParameter(qualifier, parameters[0]);
}
private static boolean resolvesToParameter(PsiExpression expression, PsiParameter parameter) {
private static boolean resolvesToParameter(PsiExpression expression, PsiVariable parameter) {
return expression instanceof PsiReferenceExpression && ((PsiReferenceExpression)expression).resolve() == parameter;
}
@@ -280,7 +280,7 @@ public class LambdaCanBeMethodReferenceInspection extends BaseJavaBatchLocalInsp
}
@Nullable
private static PsiMethod getNonAmbiguousReceiver(PsiParameter[] parameters, @NotNull PsiMethod psiMethod) {
private static PsiMethod getNonAmbiguousReceiver(PsiVariable[] parameters, @NotNull PsiMethod psiMethod) {
String methodName = psiMethod.getName();
PsiClass containingClass = psiMethod.getContainingClass();
if (containingClass == null) return null;
@@ -304,7 +304,7 @@ public class LambdaCanBeMethodReferenceInspection extends BaseJavaBatchLocalInsp
return psiMethod;
}
private static boolean isPairedNoReceiver(PsiParameter[] parameters,
private static boolean isPairedNoReceiver(PsiVariable[] parameters,
PsiType receiverType,
PsiMethod method) {
final PsiParameter[] nonReceiverCandidateParams = method.getParameterList().getParameters();
@@ -316,7 +316,7 @@ public class LambdaCanBeMethodReferenceInspection extends BaseJavaBatchLocalInsp
@Nullable
public static String createMethodReferenceText(final PsiElement element,
final PsiType functionalInterfaceType,
final PsiParameter[] parameters) {
final PsiVariable[] parameters) {
if (element instanceof PsiMethodCallExpression) {
final PsiMethodCallExpression methodCall = (PsiMethodCallExpression)element;
@@ -382,7 +382,7 @@ public class LambdaCanBeMethodReferenceInspection extends BaseJavaBatchLocalInsp
@Nullable
private static String getQualifierTextByMethodCall(final PsiMethodCallExpression methodCall,
final PsiType functionalInterfaceType,
final PsiParameter[] parameters,
final PsiVariable[] parameters,
final PsiMethod psiMethod,
final PsiSubstitutor substitutor) {
@@ -427,7 +427,7 @@ public class LambdaCanBeMethodReferenceInspection extends BaseJavaBatchLocalInsp
}
@Nullable
private static String composeReceiverQualifierText(PsiParameter[] parameters,
private static String composeReceiverQualifierText(PsiVariable[] parameters,
PsiMethod psiMethod,
PsiClass containingClass,
@NotNull PsiExpression qualifierExpression) {
@@ -353,12 +353,9 @@ public class StreamApiMigrationInspection extends BaseJavaBatchLocalInspectionTo
final PsiCallExpression callExpression = LambdaCanBeMethodReferenceInspection.extractMethodCallFromBlock(block);
if (callExpression != null) {
final PsiClassType functionalType = createDefaultConsumerType(project, variable);
String methodReferenceText = null;
if(variable instanceof PsiParameter) {
final PsiParameter[] parameters = {(PsiParameter)variable};
methodReferenceText =
LambdaCanBeMethodReferenceInspection.convertToMethodReference(block, parameters, functionalType, null);
}
final PsiVariable[] parameters = {variable};
String methodReferenceText =
LambdaCanBeMethodReferenceInspection.convertToMethodReference(block, parameters, functionalType, null);
if (methodReferenceText != null) {
return methodReferenceText;
}
@@ -597,26 +594,21 @@ public class StreamApiMigrationInspection extends BaseJavaBatchLocalInspectionTo
static class TerminalBlock {
private PsiVariable myVariable;
private PsiStatement[] myStatements;
private int myFrom, myTo;
private TerminalBlock(PsiVariable variable, PsiStatement[] statements, int from, int to) {
private TerminalBlock(PsiVariable variable, PsiStatement[] statements) {
myVariable = variable;
myStatements = statements;
myFrom = from;
myTo = to;
flatten();
}
private void flatten() {
while(myTo - myFrom == 1 && myStatements[myFrom] instanceof PsiBlockStatement) {
myStatements = ((PsiBlockStatement)myStatements[myFrom]).getCodeBlock().getStatements();
myFrom = 0;
myTo = myStatements.length;
while(myStatements.length == 1 && myStatements[0] instanceof PsiBlockStatement) {
myStatements = ((PsiBlockStatement)myStatements[0]).getCodeBlock().getStatements();
}
}
PsiStatement getSingleStatement() {
return myTo - myFrom == 1 ? myStatements[myFrom] : null;
return myStatements.length == 1 ? myStatements[0] : null;
}
/**
@@ -673,17 +665,14 @@ public class StreamApiMigrationInspection extends BaseJavaBatchLocalInspectionTo
}
if(op != null && ReferencesSearch.search(myVariable, new LocalSearchScope(body)).findFirst() == null) {
myVariable = foreachStatement.getIterationParameter();
myStatements = new PsiStatement[] {body};
myFrom = 0;
myTo = 1;
flatten();
replaceWith(body);
return op;
}
}
}
// extract map
if(myTo > myFrom+1) {
PsiStatement first = myStatements[myFrom];
if(myStatements.length > 1) {
PsiStatement first = myStatements[0];
if(first instanceof PsiDeclarationStatement) {
PsiDeclarationStatement decl = (PsiDeclarationStatement)first;
PsiElement[] elements = decl.getDeclaredElements();
@@ -694,12 +683,13 @@ public class StreamApiMigrationInspection extends BaseJavaBatchLocalInspectionTo
// do not handle mapToPrimitive
if(!(declaredVar.getType() instanceof PsiPrimitiveType)) {
PsiExpression initializer = declaredVar.getInitializer();
PsiStatement[] leftOver = Arrays.copyOfRange(myStatements, 1, myStatements.length);
if (initializer != null &&
ReferencesSearch.search(myVariable, new LocalSearchScope(Arrays.copyOfRange(myStatements, myFrom + 1, myTo)))
ReferencesSearch.search(myVariable, new LocalSearchScope(leftOver))
.findFirst() == null) {
MapOp op = new MapOp(initializer, myVariable);
myVariable = declaredVar;
myFrom++;
myStatements = leftOver;
flatten();
return op;
}
@@ -723,8 +713,6 @@ public class StreamApiMigrationInspection extends BaseJavaBatchLocalInspectionTo
private void replaceWith(PsiStatement statement) {
myStatements = new PsiStatement[] {statement};
myFrom = 0;
myTo = 1;
flatten();
}
@@ -734,8 +722,7 @@ public class StreamApiMigrationInspection extends BaseJavaBatchLocalInspectionTo
@Contract("_, _ -> !null")
static TerminalBlock from(PsiVariable variable, PsiStatement statement) {
PsiStatement[] statements = {statement};
return new TerminalBlock(variable, statements, 0, 1);
return new TerminalBlock(variable, new PsiStatement[] {statement});
}
@NotNull
@@ -757,12 +744,12 @@ public class StreamApiMigrationInspection extends BaseJavaBatchLocalInspectionTo
* @return the PsiElement
*/
public PsiElement convertToElement(PsiElementFactory factory) {
if (myTo - myFrom == 1) {
return myStatements[myFrom];
if (myStatements.length == 1) {
return myStatements[0];
}
PsiCodeBlock block = factory.createCodeBlock();
for (int i = myFrom; i < myTo; i++) {
block.add(myStatements[i]);
for (PsiStatement statement : myStatements) {
block.add(statement);
}
return block;
}
@@ -782,11 +769,8 @@ public class StreamApiMigrationInspection extends BaseJavaBatchLocalInspectionTo
}
}
final PsiClassType functionalInterfaceType = functionClass != null ? psiFacade.getElementFactory().createType(functionClass, samParamTypes) : null;
String methodReferenceText = null;
if(variable instanceof PsiParameter) {
final PsiParameter[] parameters = {(PsiParameter)variable};
methodReferenceText = LambdaCanBeMethodReferenceInspection.convertToMethodReference(expression, parameters, functionalInterfaceType, null);
}
final PsiVariable[] parameters = {variable};
String methodReferenceText = LambdaCanBeMethodReferenceInspection.convertToMethodReference(expression, parameters, functionalInterfaceType, null);
if (methodReferenceText != null) {
LOG.assertTrue(functionalInterfaceType != null);
result += "(" + functionalInterfaceType.getCanonicalText() + ")" + methodReferenceText;
@@ -7,6 +7,6 @@ import java.util.stream.Collectors;
public class Main {
public void test(Map<String, String[]> map) {
List<String> result = map.entrySet().stream().filter(entry -> entry.getKey().startsWith("x")).map(Map.Entry::getValue).flatMap(arr -> Arrays.stream(arr)).map(String::trim).collect(Collectors.toList());
List<String> result = map.entrySet().stream().filter(entry -> entry.getKey().startsWith("x")).map(Map.Entry::getValue).flatMap(Arrays::stream).map(String::trim).collect(Collectors.toList());
}
}