View Javadoc
1   /**
2    * BSD-style license; for more info see http://pmd.sourceforge.net/license.html
3    */
4   package net.sourceforge.pmd.lang.java.rule.basic;
5   
6   import net.sourceforge.pmd.lang.ast.Node;
7   import net.sourceforge.pmd.lang.java.ast.ASTExpression;
8   import net.sourceforge.pmd.lang.java.ast.ASTPrimaryExpression;
9   import net.sourceforge.pmd.lang.java.ast.ASTPrimaryPrefix;
10  import net.sourceforge.pmd.lang.java.ast.ASTUnaryExpression;
11  import net.sourceforge.pmd.lang.java.ast.ASTUnaryExpressionNotPlusMinus;
12  import net.sourceforge.pmd.lang.java.rule.AbstractJavaRule;
13  
14  public class AvoidMultipleUnaryOperatorsRule extends AbstractJavaRule {
15  
16  	public AvoidMultipleUnaryOperatorsRule() {
17  		super.addRuleChainVisit(ASTUnaryExpression.class);
18  		super.addRuleChainVisit(ASTUnaryExpressionNotPlusMinus.class);
19  	}
20  
21  	@Override
22  	public Object visit(ASTUnaryExpression node, Object data) {
23  		checkUnaryDescendent(node, data);
24  		return data;
25  	}
26  
27  	@Override
28  	public Object visit(ASTUnaryExpressionNotPlusMinus node, Object data) {
29  		checkUnaryDescendent(node, data);
30  		return data;
31  	}
32  
33  	private void checkUnaryDescendent(Node node, Object data) {
34  		boolean match = false;
35  		if (node.jjtGetNumChildren() == 1) {
36  			Node child = node.jjtGetChild(0);
37  			if (child instanceof ASTUnaryExpression || child instanceof ASTUnaryExpressionNotPlusMinus) {
38  				match = true;
39  			} else if (child instanceof ASTPrimaryExpression) {
40  				Node primaryExpression = child;
41  				// Skip down PrimaryExpression/PrimaryPrefix/Expression chains created by parentheses
42  				while (true) {
43  					if (primaryExpression.jjtGetNumChildren() == 1
44  							&& primaryExpression.jjtGetChild(0) instanceof ASTPrimaryPrefix
45  							&& primaryExpression.jjtGetChild(0).jjtGetNumChildren() == 1
46  							&& primaryExpression.jjtGetChild(0).jjtGetChild(0) instanceof ASTExpression
47  							&& primaryExpression.jjtGetChild(0).jjtGetChild(0).jjtGetNumChildren() == 1) {
48  						Node candidate = primaryExpression.jjtGetChild(0).jjtGetChild(0).jjtGetChild(0);
49  						if (candidate instanceof ASTUnaryExpression
50  								|| candidate instanceof ASTUnaryExpressionNotPlusMinus) {
51  							match = true;
52  							break;
53  						} else if (candidate instanceof ASTPrimaryExpression) {
54  							primaryExpression = candidate;
55  							continue;
56  						} else {
57  							break;
58  						}
59  					} else {
60  						break;
61  					}
62  				}
63  			}
64  		}
65  
66  		if (match) {
67  			addViolation(data, node);
68  		}
69  	}
70  }