private static boolean binaryExpressionsAreEquivalent(
     @NotNull PsiBinaryExpression binaryExp1, @NotNull PsiBinaryExpression binaryExp2) {
   final IElementType tokenType1 = binaryExp1.getOperationTokenType();
   if (!tokenType1.equals(binaryExp2.getOperationTokenType())) {
     return false;
   }
   final PsiExpression lhs1 = binaryExp1.getLOperand();
   final PsiExpression lhs2 = binaryExp2.getLOperand();
   final PsiExpression rhs1 = binaryExp1.getROperand();
   final PsiExpression rhs2 = binaryExp2.getROperand();
   return expressionsAreEquivalent(lhs1, lhs2) && expressionsAreEquivalent(rhs1, rhs2);
 }
  @Nullable
  private LocalQuickFix[] createNPEFixes(
      PsiExpression qualifier, PsiExpression expression, boolean onTheFly) {
    if (qualifier == null || expression == null) return null;
    if (qualifier instanceof PsiMethodCallExpression) return null;
    if (qualifier instanceof PsiLiteralExpression
        && ((PsiLiteralExpression) qualifier).getValue() == null) return null;

    try {
      final List<LocalQuickFix> fixes = new SmartList<LocalQuickFix>();

      if (PsiUtil.getLanguageLevel(qualifier).isAtLeast(LanguageLevel.JDK_1_4)) {
        final Project project = qualifier.getProject();
        final PsiElementFactory elementFactory =
            JavaPsiFacade.getInstance(project).getElementFactory();
        final PsiBinaryExpression binary =
            (PsiBinaryExpression) elementFactory.createExpressionFromText("a != null", null);
        binary.getLOperand().replace(qualifier);
        fixes.add(new AddAssertStatementFix(binary));
      }

      addSurroundWithIfFix(qualifier, fixes, onTheFly);

      if (ReplaceWithTernaryOperatorFix.isAvailable(qualifier, expression)) {
        fixes.add(new ReplaceWithTernaryOperatorFix(qualifier));
      }
      return fixes.toArray(new LocalQuickFix[fixes.size()]);
    } catch (IncorrectOperationException e) {
      LOG.error(e);
      return null;
    }
  }
Exemplo n.º 3
0
 protected static void replaceExpressionWithNegatedExpression(
     @NotNull PsiExpression newExpression, @NotNull PsiExpression expression) {
   final Project project = expression.getProject();
   final PsiElementFactory factory = JavaPsiFacade.getElementFactory(project);
   PsiExpression expressionToReplace = expression;
   final String newExpressionText = newExpression.getText();
   final String expString;
   if (BoolUtils.isNegated(expression)) {
     expressionToReplace = BoolUtils.findNegation(expression);
     expString = newExpressionText;
   } else if (ComparisonUtils.isComparison(newExpression)) {
     final PsiBinaryExpression binaryExpression = (PsiBinaryExpression) newExpression;
     final String negatedComparison =
         ComparisonUtils.getNegatedComparison(binaryExpression.getOperationTokenType());
     final PsiExpression lhs = binaryExpression.getLOperand();
     final PsiExpression rhs = binaryExpression.getROperand();
     assert rhs != null;
     expString = lhs.getText() + negatedComparison + rhs.getText();
   } else {
     if (ParenthesesUtils.getPrecedence(newExpression) > ParenthesesUtils.PREFIX_PRECEDENCE) {
       expString = "!(" + newExpressionText + ')';
     } else {
       expString = '!' + newExpressionText;
     }
   }
   final PsiExpression newCall = factory.createExpressionFromText(expString, expression);
   assert expressionToReplace != null;
   final PsiElement insertedElement = expressionToReplace.replace(newCall);
   final CodeStyleManager codeStyleManager = CodeStyleManager.getInstance(project);
   codeStyleManager.reformat(insertedElement);
 }
 @Override
 public void visitBinaryExpression(@NotNull PsiBinaryExpression expression) {
   super.visitBinaryExpression(expression);
   final PsiExpression rhs = expression.getROperand();
   if (!(rhs != null)) {
     return;
   }
   if (!ComparisonUtils.isComparison(expression)) {
     return;
   }
   if (ComparisonUtils.isEqualityComparison(expression)) {
     return;
   }
   final PsiExpression lhs = expression.getLOperand();
   if (!isCharacter(lhs)) {
     return;
   }
   if (!isCharacter(rhs)) {
     return;
   }
   if (NonNlsUtils.isNonNlsAnnotated(lhs) || NonNlsUtils.isNonNlsAnnotated(rhs)) {
     return;
   }
   registerError(expression);
 }
 private static String buildToOffsetText(PsiExpression expression, boolean plusOne) {
   expression = ParenthesesUtils.stripParentheses(expression);
   if (expression == null) {
     return null;
   }
   if (!plusOne) {
     return expression.getText();
   }
   if (expression instanceof PsiBinaryExpression) {
     final PsiBinaryExpression binaryExpression = (PsiBinaryExpression) expression;
     final IElementType tokenType = binaryExpression.getOperationTokenType();
     if (tokenType == JavaTokenType.MINUS) {
       final PsiExpression rhs = binaryExpression.getROperand();
       if (ExpressionUtils.isOne(rhs)) {
         return binaryExpression.getLOperand().getText();
       }
     }
   }
   final int precedence = ParenthesesUtils.getPrecedence(expression);
   if (precedence > ParenthesesUtils.ADDITIVE_PRECEDENCE) {
     return '(' + expression.getText() + ")+1";
   } else {
     return expression.getText() + "+1";
   }
 }
 @Override
 public void visitBinaryExpression(PsiBinaryExpression expression) {
   final IElementType tokenType = expression.getOperationTokenType();
   if (JavaTokenType.OROR != tokenType) {
     return;
   }
   final PsiExpression lhs = expression.getLOperand();
   final PsiExpression rhs = expression.getROperand();
   final Pair<PsiReferenceExpression, PsiExpression> pair1 = getReferenceExpressionPair(lhs);
   final Pair<PsiReferenceExpression, PsiExpression> pair2 = getReferenceExpressionPair(rhs);
   if (pair1 == null || pair2 == null) {
     return;
   }
   final PsiExpression expression1 = pair1.getSecond();
   final PsiExpression expression2 = pair2.getSecond();
   if (expression1 == null || expression2 == null) {
     return;
   }
   final Project project = expression1.getProject();
   final JavaPsiFacade psiFacade = JavaPsiFacade.getInstance(project);
   final PsiConstantEvaluationHelper constantEvaluationHelper =
       psiFacade.getConstantEvaluationHelper();
   final Object constant1 = constantEvaluationHelper.computeConstantExpression(expression1);
   final Object constant2 = constantEvaluationHelper.computeConstantExpression(expression2);
   if (constant1 == null || constant2 == null || constant1 == constant2) {
     return;
   }
   final PsiReferenceExpression referenceExpression1 = pair1.getFirst();
   final PsiReferenceExpression referenceExpression2 = pair2.getFirst();
   if (referenceExpression1.resolve() == referenceExpression2.resolve()) {
     registerError(expression);
   }
 }
 private boolean checkCondition(@Nullable PsiExpression condition, @Nullable PsiStatement body) {
   if (body == null) {
     return false;
   }
   if (!(condition instanceof PsiBinaryExpression)) {
     return false;
   }
   final PsiBinaryExpression binaryExpression = (PsiBinaryExpression) condition;
   final IElementType tokenType = binaryExpression.getOperationTokenType();
   final PsiExpression lhs = binaryExpression.getLOperand();
   final PsiExpression rhs = binaryExpression.getROperand();
   if (JavaTokenType.ANDAND == tokenType) {
     return checkCondition(lhs, body) || checkCondition(rhs, body);
   }
   if (JavaTokenType.EQEQ != tokenType) {
     return false;
   }
   if (rhs == null) {
     return false;
   }
   if (PsiUtil.isConstantExpression(lhs)) {
     return checkConstantValueVariableUse(rhs, lhs, body);
   } else if (PsiUtil.isConstantExpression(rhs)) {
     return checkConstantValueVariableUse(lhs, rhs, body);
   }
   return false;
 }
    public void applyFix(@NotNull Project project, @NotNull ProblemDescriptor descriptor) {
      try {
        PsiBinaryExpression binaryExpression = (PsiBinaryExpression) descriptor.getPsiElement();
        IElementType opSign = binaryExpression.getOperationSign().getTokenType();
        PsiExpression lExpr = binaryExpression.getLOperand();
        PsiExpression rExpr = binaryExpression.getROperand();
        if (rExpr == null) return;

        PsiElementFactory factory = JavaPsiFacade.getInstance(project).getElementFactory();
        PsiMethodCallExpression equalsCall =
            (PsiMethodCallExpression) factory.createExpressionFromText("a.equals(b)", null);

        equalsCall.getMethodExpression().getQualifierExpression().replace(lExpr);
        equalsCall.getArgumentList().getExpressions()[0].replace(rExpr);

        PsiExpression result = (PsiExpression) binaryExpression.replace(equalsCall);

        if (opSign == JavaTokenType.NE) {
          PsiPrefixExpression negation =
              (PsiPrefixExpression) factory.createExpressionFromText("!a", null);
          negation.getOperand().replace(result);
          result.replace(negation);
        }
      } catch (IncorrectOperationException e) {
        LOG.error(e);
      }
    }
Exemplo n.º 9
0
  @NotNull
  private static PsiExpression psiToClsExpression(
      final PsiExpression expr, @Nullable final ClsElementImpl parent) {
    if (expr instanceof PsiLiteralExpression) {
      return new ClsLiteralExpressionImpl(
          parent, expr.getText(), expr.getType(), ((PsiLiteralExpression) expr).getValue());
    } else if (expr instanceof PsiPrefixExpression) {
      final PsiPrefixExpression prefixExpr = (PsiPrefixExpression) expr;
      final ClsJavaTokenImpl operation =
          new ClsJavaTokenImpl(
              null, prefixExpr.getOperationTokenType(), prefixExpr.getOperationSign().getText());
      final ClsLiteralExpressionImpl literal =
          (ClsLiteralExpressionImpl) psiToClsExpression(prefixExpr.getOperand(), null);
      return new ClsPrefixExpressionImpl(parent, operation, literal);
    } else if (expr instanceof PsiClassObjectAccessExpression) {
      final String canonicalClassText =
          ((PsiClassObjectAccessExpression) expr).getOperand().getType().getCanonicalText();
      return new ClsClassObjectAccessExpressionImpl(parent, canonicalClassText);
    } else if (expr instanceof PsiReferenceExpression) {
      return new ClsReferenceExpressionImpl(parent, (PsiReferenceExpression) expr);
    } else if (expr instanceof PsiBinaryExpression) {
      final PsiBinaryExpression binaryExpr = (PsiBinaryExpression) expr;
      final PsiExpression lOperand = psiToClsExpression(binaryExpr.getLOperand(), null);
      final ClsJavaTokenImpl operation =
          new ClsJavaTokenImpl(
              null, binaryExpr.getOperationTokenType(), binaryExpr.getOperationSign().getText());
      final PsiExpression rOperand = psiToClsExpression(binaryExpr.getROperand(), null);
      if (lOperand instanceof ClsLiteralExpressionImpl) {
        return new ClsBinaryExpressionImpl(
            parent,
            (ClsLiteralExpressionImpl) lOperand,
            operation,
            (ClsLiteralExpressionImpl) rOperand);
      } else if (lOperand instanceof ClsPrefixExpressionImpl) {
        return new ClsBinaryExpressionImpl(
            parent,
            (ClsPrefixExpressionImpl) lOperand,
            operation,
            (ClsLiteralExpressionImpl) rOperand);
      }
    } else {
      final PsiConstantEvaluationHelper evaluator =
          JavaPsiFacade.getInstance(expr.getProject()).getConstantEvaluationHelper();
      final Object value = evaluator.computeConstantExpression(expr);
      if (value != null) {
        return new ClsLiteralExpressionImpl(parent, expr.getText(), expr.getType(), value);
      }
    }

    LOG.error("Unable to compute expression value: " + expr);
    return null;
  }
 @Override
 public void visitBinaryExpression(@NotNull PsiBinaryExpression expression) {
   super.visitBinaryExpression(expression);
   if (!ComparisonUtils.isComparison(expression)) {
     return;
   }
   final PsiExpression lhs = expression.getLOperand();
   final PsiExpression rhs = expression.getROperand();
   if (rhs == null || !isConstantExpression(lhs) || isConstantExpression(rhs)) {
     return;
   }
   registerError(expression);
 }
 @Override
 protected void doFix(Project project, ProblemDescriptor descriptor)
     throws IncorrectOperationException {
   final PsiElement element = descriptor.getPsiElement();
   if (!(element instanceof PsiBinaryExpression)) {
     return;
   }
   final PsiBinaryExpression binaryExpression = (PsiBinaryExpression) element;
   final PsiExpression lhs = binaryExpression.getLOperand();
   final String lhsText = lhs.getText();
   final PsiExpression rhs = binaryExpression.getROperand();
   if (rhs == null) {
     return;
   }
   final String rhsText = rhs.getText();
   replaceExpression(binaryExpression, lhsText + "&&" + rhsText);
 }
 @Override
 protected void doFix(Project project, ProblemDescriptor descriptor)
     throws IncorrectOperationException {
   final PsiBinaryExpression expression = (PsiBinaryExpression) descriptor.getPsiElement();
   final PsiExpression lhs = expression.getLOperand();
   final PsiExpression rhs = expression.getROperand();
   final PsiJavaToken sign = expression.getOperationSign();
   final String newExpressionText;
   if (lhs instanceof PsiMethodCallExpression) {
     final PsiMethodCallExpression callExpression = (PsiMethodCallExpression) lhs;
     newExpressionText = createContainsExpressionText(callExpression, sign, false);
   } else {
     final PsiMethodCallExpression callExpression = (PsiMethodCallExpression) rhs;
     assert callExpression != null;
     newExpressionText = createContainsExpressionText(callExpression, sign, true);
   }
   replaceExpression(expression, newExpressionText);
 }
 @Override
 public void doFix(Project project, ProblemDescriptor descriptor)
     throws IncorrectOperationException {
   final PsiBinaryExpression expression = (PsiBinaryExpression) descriptor.getPsiElement();
   final PsiExpression rhs = expression.getROperand();
   if (rhs == null) {
     return;
   }
   final String flippedComparison =
       ComparisonUtils.getFlippedComparison(expression.getOperationTokenType());
   if (flippedComparison == null) {
     return;
   }
   final PsiExpression lhs = expression.getLOperand();
   final String rhsText = rhs.getText();
   final String lhsText = lhs.getText();
   replaceExpression(expression, rhsText + ' ' + flippedComparison + ' ' + lhsText);
 }
 @Override
 @NotNull
 public String buildErrorString(Object... infos) {
   final PsiBinaryExpression expression = (PsiBinaryExpression) infos[0];
   final PsiExpression lhs = expression.getLOperand();
   final PsiJavaToken sign = expression.getOperationSign();
   final String text;
   if (lhs instanceof PsiMethodCallExpression) {
     final PsiMethodCallExpression callExpression = (PsiMethodCallExpression) lhs;
     text = createContainsExpressionText(callExpression, sign, false);
   } else {
     final PsiMethodCallExpression callExpression =
         (PsiMethodCallExpression) expression.getROperand();
     assert callExpression != null;
     text = createContainsExpressionText(callExpression, sign, true);
   }
   return InspectionGadgetsBundle.message(
       "indexof.replaceable.by.contains.problem.descriptor", text);
 }
 @Nullable
 private static PsiReferenceExpression getReferenceFromNullCheck(
     PsiBinaryExpression expression) {
   final PsiExpression lhs = ParenthesesUtils.stripParentheses(expression.getLOperand());
   final PsiExpression rhs = ParenthesesUtils.stripParentheses(expression.getROperand());
   if (lhs instanceof PsiReferenceExpression) {
     if (!(rhs instanceof PsiLiteralExpression && PsiType.NULL.equals(rhs.getType()))) {
       return null;
     }
     return (PsiReferenceExpression) lhs;
   } else if (rhs instanceof PsiReferenceExpression) {
     if (!(lhs instanceof PsiLiteralExpression && PsiType.NULL.equals(lhs.getType()))) {
       return null;
     }
     return (PsiReferenceExpression) rhs;
   } else {
     return null;
   }
 }
 @Override
 public void doFix(Project project, ProblemDescriptor descriptor)
     throws IncorrectOperationException {
   final PsiElement element = descriptor.getPsiElement();
   final PsiBinaryExpression binaryExpression =
       PsiTreeUtil.getParentOfType(element, PsiBinaryExpression.class);
   if (binaryExpression == null) {
     return;
   }
   final PsiExpression lhs = binaryExpression.getLOperand();
   final PsiExpression rhs = binaryExpression.getROperand();
   if (rhs == null) {
     return;
   }
   if (PsiTreeUtil.isAncestor(rhs, element, false)) {
     replaceExpression(binaryExpression, lhs.getText());
   } else if (PsiTreeUtil.isAncestor(lhs, element, false)) {
     replaceExpression(binaryExpression, rhs.getText());
   }
 }
 @Nullable
 private static Pair<PsiReferenceExpression, PsiExpression> getReferenceExpressionPair(
     PsiExpression expression) {
   if (!(expression instanceof PsiBinaryExpression)) {
     return null;
   }
   final PsiBinaryExpression binaryExpression = (PsiBinaryExpression) expression;
   final IElementType tokenType = binaryExpression.getOperationTokenType();
   if (JavaTokenType.NE != tokenType) {
     return null;
   }
   final PsiExpression lhs = binaryExpression.getLOperand();
   final PsiExpression rhs = binaryExpression.getROperand();
   if (lhs instanceof PsiReferenceExpression) {
     final PsiReferenceExpression lref = (PsiReferenceExpression) lhs;
     return new Pair(lref, rhs);
   } else if (rhs instanceof PsiReferenceExpression) {
     final PsiReferenceExpression rref = (PsiReferenceExpression) rhs;
     return new Pair(rref, lhs);
   }
   return null;
 }
 @Override
 public void visitBinaryExpression(PsiBinaryExpression expression) {
   super.visitBinaryExpression(expression);
   final PsiExpression rhs = expression.getROperand();
   if (rhs == null) {
     return;
   }
   if (!ComparisonUtils.isComparison(expression)) {
     return;
   }
   final PsiExpression lhs = expression.getLOperand();
   if (lhs instanceof PsiMethodCallExpression) {
     final PsiJavaToken sign = expression.getOperationSign();
     if (canBeReplacedByContains(lhs, sign, rhs, false)) {
       registerError(expression, expression);
     }
   } else if (rhs instanceof PsiMethodCallExpression) {
     final PsiJavaToken sign = expression.getOperationSign();
     if (canBeReplacedByContains(rhs, sign, lhs, true)) {
       registerError(expression, expression);
     }
   }
 }
 @Nullable
 private static String buildFromOffsetText(PsiExpression expression, PsiLocalVariable variable)
     throws IncorrectOperationException {
   expression = ParenthesesUtils.stripParentheses(expression);
   if (expression == null) {
     return null;
   }
   final String expressionText = expression.getText();
   final String variableName = variable.getName();
   if (expressionText.equals(variableName)) {
     final PsiExpression initialValue = variable.getInitializer();
     if (initialValue == null) {
       return null;
     }
     return initialValue.getText();
   }
   if (expression instanceof PsiBinaryExpression) {
     final PsiBinaryExpression binaryExpression = (PsiBinaryExpression) expression;
     final PsiExpression lhs = binaryExpression.getLOperand();
     final PsiExpression rhs = binaryExpression.getROperand();
     final String rhsText = buildFromOffsetText(rhs, variable);
     final PsiJavaToken sign = binaryExpression.getOperationSign();
     final IElementType tokenType = sign.getTokenType();
     if (ExpressionUtils.isZero(lhs)) {
       if (tokenType.equals(JavaTokenType.MINUS)) {
         return '-' + rhsText;
       }
       return rhsText;
     }
     final String lhsText = buildFromOffsetText(lhs, variable);
     if (ExpressionUtils.isZero(rhs)) {
       return lhsText;
     }
     return collapseConstant(lhsText + sign.getText() + rhsText, variable);
   }
   return collapseConstant(expression.getText(), variable);
 }
 @Nullable
 private String createListIterationText(@NotNull PsiForStatement forStatement) {
   final PsiBinaryExpression condition =
       (PsiBinaryExpression) ParenthesesUtils.stripParentheses(forStatement.getCondition());
   if (condition == null) {
     return null;
   }
   final PsiExpression lhs = ParenthesesUtils.stripParentheses(condition.getLOperand());
   if (lhs == null) {
     return null;
   }
   final PsiExpression rhs = ParenthesesUtils.stripParentheses(condition.getROperand());
   if (rhs == null) {
     return null;
   }
   final IElementType tokenType = condition.getOperationTokenType();
   final String indexName;
   PsiExpression collectionSize;
   if (JavaTokenType.LT.equals(tokenType)) {
     indexName = lhs.getText();
     collectionSize = rhs;
   } else if (JavaTokenType.GT.equals(tokenType)) {
     indexName = rhs.getText();
     collectionSize = lhs;
   } else {
     return null;
   }
   if (collectionSize instanceof PsiReferenceExpression) {
     final PsiReferenceExpression referenceExpression = (PsiReferenceExpression) collectionSize;
     final PsiElement target = referenceExpression.resolve();
     if (target instanceof PsiVariable) {
       final PsiVariable variable = (PsiVariable) target;
       collectionSize = ParenthesesUtils.stripParentheses(variable.getInitializer());
     }
   }
   if (!(collectionSize instanceof PsiMethodCallExpression)) {
     return null;
   }
   final PsiMethodCallExpression methodCallExpression =
       (PsiMethodCallExpression) ParenthesesUtils.stripParentheses(collectionSize);
   if (methodCallExpression == null) {
     return null;
   }
   final PsiReferenceExpression listLengthExpression =
       methodCallExpression.getMethodExpression();
   final PsiExpression qualifier =
       ParenthesesUtils.stripParentheses(listLengthExpression.getQualifierExpression());
   final PsiReferenceExpression listReference;
   if (qualifier instanceof PsiReferenceExpression) {
     listReference = (PsiReferenceExpression) qualifier;
   } else {
     listReference = null;
   }
   PsiType parameterType;
   if (listReference == null) {
     parameterType = extractListTypeFromContainingClass(forStatement);
   } else {
     final PsiType type = listReference.getType();
     if (type == null) {
       return null;
     }
     parameterType = extractContentTypeFromType(type);
   }
   if (parameterType == null) {
     parameterType = TypeUtils.getObjectType(forStatement);
   }
   final String typeString = parameterType.getCanonicalText();
   final PsiVariable listVariable;
   if (listReference == null) {
     listVariable = null;
   } else {
     final PsiElement target = listReference.resolve();
     if (!(target instanceof PsiVariable)) {
       return null;
     }
     listVariable = (PsiVariable) target;
   }
   final PsiStatement body = forStatement.getBody();
   final PsiStatement firstStatement = getFirstStatement(body);
   final boolean isDeclaration =
       isListElementDeclaration(firstStatement, listVariable, indexName, parameterType);
   final String contentVariableName;
   @NonNls final String finalString;
   final PsiStatement statementToSkip;
   if (isDeclaration) {
     final PsiDeclarationStatement declarationStatement =
         (PsiDeclarationStatement) firstStatement;
     assert declarationStatement != null;
     final PsiElement[] declaredElements = declarationStatement.getDeclaredElements();
     final PsiElement declaredElement = declaredElements[0];
     if (!(declaredElement instanceof PsiVariable)) {
       return null;
     }
     final PsiVariable variable = (PsiVariable) declaredElement;
     contentVariableName = variable.getName();
     statementToSkip = declarationStatement;
     if (variable.hasModifierProperty(PsiModifier.FINAL)) {
       finalString = "final ";
     } else {
       finalString = "";
     }
   } else {
     final String collectionName;
     if (listReference == null) {
       collectionName = null;
     } else {
       collectionName = listReference.getReferenceName();
     }
     contentVariableName = createNewVariableName(forStatement, parameterType, collectionName);
     finalString = "";
     statementToSkip = null;
   }
   @NonNls final StringBuilder out = new StringBuilder();
   out.append("for(");
   out.append(finalString);
   out.append(typeString);
   out.append(' ');
   out.append(contentVariableName);
   out.append(": ");
   @NonNls final String listName;
   if (listReference == null) {
     listName = "this";
   } else {
     listName = listReference.getText();
   }
   out.append(listName);
   out.append(')');
   if (body != null) {
     replaceCollectionGetAccess(
         body, contentVariableName, listVariable, indexName, statementToSkip, out);
   }
   return out.toString();
 }
 @Nullable
 private String createArrayIterationText(@NotNull PsiForStatement forStatement) {
   final PsiExpression condition = forStatement.getCondition();
   final PsiBinaryExpression strippedCondition =
       (PsiBinaryExpression) ParenthesesUtils.stripParentheses(condition);
   if (strippedCondition == null) {
     return null;
   }
   final PsiExpression lhs = ParenthesesUtils.stripParentheses(strippedCondition.getLOperand());
   if (lhs == null) {
     return null;
   }
   final PsiExpression rhs = ParenthesesUtils.stripParentheses(strippedCondition.getROperand());
   if (rhs == null) {
     return null;
   }
   final IElementType tokenType = strippedCondition.getOperationTokenType();
   final PsiReferenceExpression arrayLengthExpression;
   final String indexName;
   if (tokenType.equals(JavaTokenType.LT)) {
     arrayLengthExpression = (PsiReferenceExpression) ParenthesesUtils.stripParentheses(rhs);
     indexName = lhs.getText();
   } else if (tokenType.equals(JavaTokenType.GT)) {
     arrayLengthExpression = (PsiReferenceExpression) ParenthesesUtils.stripParentheses(lhs);
     indexName = rhs.getText();
   } else {
     return null;
   }
   if (arrayLengthExpression == null) {
     return null;
   }
   PsiReferenceExpression arrayReference =
       (PsiReferenceExpression) arrayLengthExpression.getQualifierExpression();
   if (arrayReference == null) {
     final PsiElement target = arrayLengthExpression.resolve();
     if (!(target instanceof PsiVariable)) {
       return null;
     }
     final PsiVariable variable = (PsiVariable) target;
     final PsiExpression initializer = variable.getInitializer();
     if (!(initializer instanceof PsiReferenceExpression)) {
       return null;
     }
     final PsiReferenceExpression referenceExpression = (PsiReferenceExpression) initializer;
     arrayReference = (PsiReferenceExpression) referenceExpression.getQualifierExpression();
     if (arrayReference == null) {
       return null;
     }
   }
   final PsiType type = arrayReference.getType();
   if (!(type instanceof PsiArrayType)) {
     return null;
   }
   final PsiArrayType arrayType = (PsiArrayType) type;
   final PsiType componentType = arrayType.getComponentType();
   final String typeText = componentType.getCanonicalText();
   final PsiElement target = arrayReference.resolve();
   if (!(target instanceof PsiVariable)) {
     return null;
   }
   final PsiVariable arrayVariable = (PsiVariable) target;
   final PsiStatement body = forStatement.getBody();
   final PsiStatement firstStatement = getFirstStatement(body);
   final boolean isDeclaration =
       isArrayElementDeclaration(firstStatement, arrayVariable, indexName);
   final String contentVariableName;
   @NonNls final String finalString;
   final PsiStatement statementToSkip;
   if (isDeclaration) {
     final PsiDeclarationStatement declarationStatement =
         (PsiDeclarationStatement) firstStatement;
     assert declarationStatement != null;
     final PsiElement[] declaredElements = declarationStatement.getDeclaredElements();
     final PsiElement declaredElement = declaredElements[0];
     if (!(declaredElement instanceof PsiVariable)) {
       return null;
     }
     final PsiVariable variable = (PsiVariable) declaredElement;
     if (VariableAccessUtils.variableIsAssigned(variable, forStatement)) {
       final String collectionName = arrayReference.getReferenceName();
       contentVariableName = createNewVariableName(forStatement, componentType, collectionName);
       final Project project = forStatement.getProject();
       final CodeStyleSettings codeStyleSettings = CodeStyleSettingsManager.getSettings(project);
       if (codeStyleSettings.GENERATE_FINAL_LOCALS) {
         finalString = "final ";
       } else {
         finalString = "";
       }
       statementToSkip = null;
     } else {
       contentVariableName = variable.getName();
       statementToSkip = declarationStatement;
       if (variable.hasModifierProperty(PsiModifier.FINAL)) {
         finalString = "final ";
       } else {
         finalString = "";
       }
     }
   } else {
     final String collectionName = arrayReference.getReferenceName();
     contentVariableName = createNewVariableName(forStatement, componentType, collectionName);
     final Project project = forStatement.getProject();
     final CodeStyleSettings codeStyleSettings = CodeStyleSettingsManager.getSettings(project);
     if (codeStyleSettings.GENERATE_FINAL_LOCALS) {
       finalString = "final ";
     } else {
       finalString = "";
     }
     statementToSkip = null;
   }
   @NonNls final StringBuilder out = new StringBuilder();
   out.append("for(");
   out.append(finalString);
   out.append(typeText);
   out.append(' ');
   out.append(contentVariableName);
   out.append(": ");
   final String arrayName = arrayReference.getText();
   out.append(arrayName);
   out.append(')');
   if (body != null) {
     replaceArrayAccess(
         body, contentVariableName, arrayVariable, indexName, statementToSkip, out);
   }
   return out.toString();
 }
 @Override
 public void visitBinaryExpression(PsiBinaryExpression expression) {
   super.visitBinaryExpression(expression);
   final IElementType operationTokenType = expression.getOperationTokenType();
   final PsiExpression lhs = ParenthesesUtils.stripParentheses(expression.getLOperand());
   final PsiExpression rhs = ParenthesesUtils.stripParentheses(expression.getROperand());
   final PsiBinaryExpression binaryExpression;
   final PsiExpression possibleInstanceofExpression;
   if (operationTokenType.equals(JavaTokenType.ANDAND)) {
     if (lhs instanceof PsiBinaryExpression) {
       binaryExpression = (PsiBinaryExpression) lhs;
       possibleInstanceofExpression = rhs;
     } else if (rhs instanceof PsiBinaryExpression) {
       binaryExpression = (PsiBinaryExpression) rhs;
       possibleInstanceofExpression = lhs;
     } else {
       return;
     }
     final IElementType tokenType = binaryExpression.getOperationTokenType();
     if (!tokenType.equals(JavaTokenType.NE)) {
       return;
     }
   } else if (operationTokenType.equals(JavaTokenType.OROR)) {
     if (lhs instanceof PsiBinaryExpression && rhs instanceof PsiPrefixExpression) {
       final PsiPrefixExpression prefixExpression = (PsiPrefixExpression) rhs;
       final IElementType prefixTokenType = prefixExpression.getOperationTokenType();
       if (!JavaTokenType.EXCL.equals(prefixTokenType)) {
         return;
       }
       binaryExpression = (PsiBinaryExpression) lhs;
       possibleInstanceofExpression =
           ParenthesesUtils.stripParentheses(prefixExpression.getOperand());
     } else if (rhs instanceof PsiBinaryExpression && lhs instanceof PsiPrefixExpression) {
       final PsiPrefixExpression prefixExpression = (PsiPrefixExpression) lhs;
       final IElementType prefixTokenType = prefixExpression.getOperationTokenType();
       if (!JavaTokenType.EXCL.equals(prefixTokenType)) {
         return;
       }
       binaryExpression = (PsiBinaryExpression) rhs;
       possibleInstanceofExpression =
           ParenthesesUtils.stripParentheses(prefixExpression.getOperand());
     } else {
       return;
     }
     final IElementType tokenType = binaryExpression.getOperationTokenType();
     if (!tokenType.equals(JavaTokenType.EQEQ)) {
       return;
     }
   } else {
     return;
   }
   final PsiReferenceExpression referenceExpression1 =
       getReferenceFromNullCheck(binaryExpression);
   if (referenceExpression1 == null) {
     return;
   }
   final PsiReferenceExpression referenceExpression2 =
       getReferenceFromInstanceofExpression(possibleInstanceofExpression);
   if (!referencesEqual(referenceExpression1, referenceExpression2)) {
     return;
   }
   registerError(binaryExpression);
 }
 @Nullable
 private static String getCollectionsAddAllText(PsiForStatement forStatement)
     throws IncorrectOperationException {
   final PsiExpression expression = forStatement.getCondition();
   final PsiBinaryExpression condition =
       (PsiBinaryExpression) ParenthesesUtils.stripParentheses(expression);
   if (condition == null) {
     return null;
   }
   final PsiStatement initialization = forStatement.getInitialization();
   if (initialization == null) {
     return null;
   }
   if (!(initialization instanceof PsiDeclarationStatement)) {
     return null;
   }
   final PsiDeclarationStatement declaration = (PsiDeclarationStatement) initialization;
   final PsiElement[] declaredElements = declaration.getDeclaredElements();
   if (declaredElements.length != 1) {
     return null;
   }
   final PsiElement declaredElement = declaredElements[0];
   if (!(declaredElement instanceof PsiLocalVariable)) {
     return null;
   }
   final PsiLocalVariable variable = (PsiLocalVariable) declaredElement;
   final String collectionText = buildCollectionText(forStatement);
   final PsiArrayAccessExpression arrayAccessExpression = getArrayAccessExpression(forStatement);
   if (arrayAccessExpression == null) {
     return null;
   }
   final PsiExpression arrayExpression = arrayAccessExpression.getArrayExpression();
   final String arrayText = arrayExpression.getText();
   final PsiExpression indexExpression = arrayAccessExpression.getIndexExpression();
   final String fromOffsetText = buildFromOffsetText(indexExpression, variable);
   if (fromOffsetText == null) {
     return null;
   }
   final PsiExpression limit;
   final IElementType tokenType = condition.getOperationTokenType();
   if (tokenType == JavaTokenType.LT || tokenType == JavaTokenType.LE) {
     limit = condition.getROperand();
   } else {
     limit = condition.getLOperand();
   }
   @NonNls
   final String toOffsetText =
       buildToOffsetText(limit, tokenType == JavaTokenType.LE || tokenType == JavaTokenType.GE);
   if (toOffsetText == null) {
     return null;
   }
   if (fromOffsetText.equals("0")
       && toOffsetText.equals(arrayText + ".length")
       && PsiUtil.isLanguageLevel5OrHigher(forStatement)) {
     return "java.util.Collections.addAll(" + collectionText + ',' + arrayText + ");";
   } else {
     @NonNls final StringBuilder buffer = new StringBuilder();
     buffer.append(collectionText);
     buffer.append('.');
     buffer.append("addAll(java.util.Arrays.asList(");
     buffer.append(arrayText);
     buffer.append(')');
     if (!fromOffsetText.equals("0") || !toOffsetText.equals(arrayText + ".length")) {
       buffer.append(".subList(");
       buffer.append(fromOffsetText);
       buffer.append(", ");
       buffer.append(toOffsetText);
       buffer.append(')');
     }
     buffer.append(");");
     return buffer.toString();
   }
 }
  public boolean processUsage(
      @NotNull EncapsulateFieldUsageInfo usage,
      @NotNull EncapsulateFieldsDescriptor descriptor,
      PsiMethod setter,
      PsiMethod getter) {
    final PsiElement element = usage.getElement();
    if (!(element instanceof PsiReferenceExpression)) return false;

    final FieldDescriptor fieldDescriptor = usage.getFieldDescriptor();
    PsiField field = fieldDescriptor.getField();
    boolean processGet = descriptor.isToEncapsulateGet();
    boolean processSet =
        descriptor.isToEncapsulateSet() && !field.hasModifierProperty(PsiModifier.FINAL);
    if (!processGet && !processSet) return true;
    PsiElementFactory factory =
        JavaPsiFacade.getInstance(descriptor.getTargetClass().getProject()).getElementFactory();

    try {
      final PsiReferenceExpression expr = (PsiReferenceExpression) element;
      final PsiElement parent = expr.getParent();
      if (parent instanceof PsiAssignmentExpression
          && expr.equals(((PsiAssignmentExpression) parent).getLExpression())) {
        PsiAssignmentExpression assignment = (PsiAssignmentExpression) parent;
        if (assignment.getRExpression() == null) return true;
        PsiJavaToken opSign = assignment.getOperationSign();
        IElementType opType = opSign.getTokenType();
        if (opType == JavaTokenType.EQ) {
          {
            if (!processSet) return true;
            final PsiExpression setterArgument = assignment.getRExpression();

            PsiMethodCallExpression methodCall =
                createSetterCall(
                    fieldDescriptor, setterArgument, expr, descriptor.getTargetClass(), setter);

            if (methodCall != null) {
              assignment.replace(methodCall);
            }
            // TODO: check if value is used!!!
          }
        } else if (opType == JavaTokenType.ASTERISKEQ
            || opType == JavaTokenType.DIVEQ
            || opType == JavaTokenType.PERCEQ
            || opType == JavaTokenType.PLUSEQ
            || opType == JavaTokenType.MINUSEQ
            || opType == JavaTokenType.LTLTEQ
            || opType == JavaTokenType.GTGTEQ
            || opType == JavaTokenType.GTGTGTEQ
            || opType == JavaTokenType.ANDEQ
            || opType == JavaTokenType.OREQ
            || opType == JavaTokenType.XOREQ) {
          {
            // Q: side effects of qualifier??!

            String opName = opSign.getText();
            LOG.assertTrue(StringUtil.endsWithChar(opName, '='));
            opName = opName.substring(0, opName.length() - 1);

            PsiExpression getExpr = expr;
            if (processGet) {
              final PsiMethodCallExpression getterCall =
                  createGetterCall(fieldDescriptor, expr, descriptor.getTargetClass(), getter);
              if (getterCall != null) {
                getExpr = getterCall;
              }
            }

            @NonNls String text = "a" + opName + "b";
            PsiBinaryExpression binExpr =
                (PsiBinaryExpression) factory.createExpressionFromText(text, expr);
            binExpr.getLOperand().replace(getExpr);
            binExpr.getROperand().replace(assignment.getRExpression());

            PsiExpression setExpr;
            if (processSet) {
              setExpr =
                  createSetterCall(
                      fieldDescriptor, binExpr, expr, descriptor.getTargetClass(), setter);
            } else {
              text = "a = b";
              PsiAssignmentExpression assignment1 =
                  (PsiAssignmentExpression) factory.createExpressionFromText(text, null);
              assignment1.getLExpression().replace(expr);
              assignment1.getRExpression().replace(binExpr);
              setExpr = assignment1;
            }

            assignment.replace(setExpr);
            // TODO: check if value is used!!!
          }
        }
      } else if (RefactoringUtil.isPlusPlusOrMinusMinus(parent)) {
        IElementType sign;
        if (parent instanceof PsiPrefixExpression) {
          sign = ((PsiPrefixExpression) parent).getOperationTokenType();
        } else {
          sign = ((PsiPostfixExpression) parent).getOperationTokenType();
        }

        PsiExpression getExpr = expr;
        if (processGet) {
          final PsiMethodCallExpression getterCall =
              createGetterCall(fieldDescriptor, expr, descriptor.getTargetClass(), getter);
          if (getterCall != null) {
            getExpr = getterCall;
          }
        }

        @NonNls String text;
        if (sign == JavaTokenType.PLUSPLUS) {
          text = "a+1";
        } else {
          text = "a-1";
        }
        PsiBinaryExpression binExpr =
            (PsiBinaryExpression) factory.createExpressionFromText(text, null);
        binExpr.getLOperand().replace(getExpr);

        PsiExpression setExpr;
        if (processSet) {
          setExpr =
              createSetterCall(fieldDescriptor, binExpr, expr, descriptor.getTargetClass(), setter);
        } else {
          text = "a = b";
          PsiAssignmentExpression assignment =
              (PsiAssignmentExpression) factory.createExpressionFromText(text, null);
          assignment.getLExpression().replace(expr);
          assignment.getRExpression().replace(binExpr);
          setExpr = assignment;
        }
        parent.replace(setExpr);
      } else {
        if (!processGet) return true;
        PsiMethodCallExpression methodCall =
            createGetterCall(fieldDescriptor, expr, descriptor.getTargetClass(), getter);

        if (methodCall != null) {
          expr.replace(methodCall);
        }
      }
    } catch (IncorrectOperationException e) {
      LOG.error(e);
    }
    return true;
  }
Exemplo n.º 25
0
 public static @NotNull PsiType getOOType(PsiBinaryExpression e) {
   if (e == null || e.getROperand() == null) return NoType;
   return getOOType(e.getLOperand().getType(), e.getROperand().getType(), e.getOperationSign());
 }