added new Unnecessary Constructor rule

git-svn-id: https://pmd.svn.sourceforge.net/svnroot/pmd/trunk@1182 51baf565-9d33-0410-a72c-fc3788e3496d
This commit is contained in:
Tom Copeland
2002-11-01 14:25:16 +00:00
parent b1aba57ca0
commit 3a86cbe699
13 changed files with 244 additions and 123 deletions

View File

@ -576,7 +576,9 @@ void FormalParameter() :
void ConstructorDeclaration() :
{}
{
[ "public" | "protected" | "private" ]
[ "public" { ((AccessNode) jjtThis).setPublic( true ); }
| "protected" { ((AccessNode) jjtThis).setProtected( true ); }
| "private" ] { ((AccessNode) jjtThis).setPrivate( true ); }
<IDENTIFIER> FormalParameters() [ "throws" NameList() ]
"{"
[ LOOKAHEAD(ExplicitConstructorInvocation()) ExplicitConstructorInvocation() ]

View File

@ -60,7 +60,7 @@
<!--<pmd reportFile="c:\jdk-1.4.html" rulesetfiles="rulesets/tmp.xml" format="html">-->
<pmd reportFile="c:\jdk-1.4.html" rulesetfiles="rulesets/tmp.xml" format="html">
<!--<fileset dir="c:\data\pmd\pmd\src\net\sourceforge\pmd\">-->
<fileset dir="c:\j2sdk1.4.1_01\src\java\lang">
<fileset dir="c:\j2sdk1.4.1_01\src\java\">
<include name="**/*.java"/>
<!--<exclude name="**/ast**/"/>-->
</fileset>
@ -83,6 +83,34 @@
</junit>
</target>
<target name="jjtree">
<jjtree target="etc/Java1.4-c.jjt" outputdirectory="src/net/sourceforge/pmd/ast" javacchome="c:/javacc2.1"/>
<javacc target="src/net/sourceforge/pmd/ast/Java1.4-c.jj" outputdirectory="src/net/sourceforge/pmd/ast" javacchome="c:/javacc2.1"/>
<delete file="src/net/sourceforge/pmd/ast/Java1.4-c.jj"/>
</target>
<target name="clean" depends="delete,compile"/>
<target name="dist" depends="clean,jar"/>
<target name="cpdjnlp" depends="dist">
<signjar jar="${lib}\pmd-${version}.jar" alias="myself" keystore="${jnlp_staging_area}myKeyStore" storepass="password"/>
<exec executable="pscp.exe" os="Windows 2000">
<arg line=" ${lib}\pmd-${version}.jar tomcopeland@pmd.sourceforge.net:/home/groups/p/pm/pmd/htdocs"/>
</exec>
</target>
<target name="run-cpd" depends="compile">
<java classname="net.sourceforge.pmd.cpd.GUI" fork="yes">
<classpath>
<path refid="classpath.path"/>
</classpath>
</java>
</target>
<path id="quilt.classpath">
<pathelement location="${lib.repo}/quilt-0.4.jar" />
<pathelement location="${lib.repo}/bcel-5.1-dev.jar" />
@ -107,12 +135,6 @@
</quilt>
</target>
<target name="jjtree">
<jjtree target="etc/Java1.4-c.jjt" outputdirectory="src/net/sourceforge/pmd/ast" javacchome="c:/javacc2.1"/>
<javacc target="src/net/sourceforge/pmd/ast/Java1.4-c.jj" outputdirectory="src/net/sourceforge/pmd/ast" javacchome="c:/javacc2.1"/>
<delete file="src/net/sourceforge/pmd/ast/Java1.4-c.jj"/>
</target>
<target name="jjtree-2">
<mkdir dir="tmp"/>
<jjtree target="etc/Java1.4-c.jjt" outputdirectory="src/net/sourceforge/pmd/ast" javacchome="/home/dpeugh/software/javacc2.1"/>
@ -125,25 +147,6 @@
</target>
<target name="clean" depends="delete,compile"/>
<target name="dist" depends="clean,jar"/>
<target name="cpdjnlp" depends="dist">
<signjar jar="${lib}\pmd-${version}.jar" alias="myself" keystore="${jnlp_staging_area}myKeyStore" storepass="password"/>
<exec executable="pscp.exe" os="Windows 2000">
<arg line=" ${lib}\pmd-${version}.jar tomcopeland@pmd.sourceforge.net:/home/groups/p/pm/pmd/htdocs"/>
</exec>
</target>
<target name="run-cpd" depends="compile">
<java classname="net.sourceforge.pmd.cpd.GUI" fork="yes">
<classpath>
<path refid="classpath.path"/>
</classpath>
</java>
</target>
</project>

View File

@ -1,5 +1,5 @@
???? 2002 - ????:
Added new rules: StringToStringRule, AvoidReassigningParametersRule
Added new rules: StringToStringRule, AvoidReassigningParametersRule, UnnecessaryConstructorRule
Fixed bug 631010: AvoidDeeplyNestedIfStmtsRule works correctly with if..else stmts now
Fixed bug 631605: OnlyOneReturn handles line spillover now.

View File

@ -0,0 +1,27 @@
/*
* User: tom
* Date: Nov 1, 2002
* Time: 9:12:42 AM
*/
package test.net.sourceforge.pmd.rules;
import net.sourceforge.pmd.rules.UnnecessaryConstructorRule;
public class UnnecessaryConstructorRuleTest extends RuleTst {
public void test1() throws Throwable {
super.runTest("UnnecessaryConstructor1.java", 1, new UnnecessaryConstructorRule());
}
public void testPrivate() throws Throwable {
super.runTest("UnnecessaryConstructor2.java", 0, new UnnecessaryConstructorRule());
}
public void testHasArgs() throws Throwable {
super.runTest("UnnecessaryConstructor3.java", 0, new UnnecessaryConstructorRule());
}
public void testHasBody() throws Throwable {
super.runTest("UnnecessaryConstructor4.java", 0, new UnnecessaryConstructorRule());
}
}

View File

@ -42,6 +42,22 @@ public class Foo {
</example>
</rule>
<rule name="UnnecessaryConstructorRule"
message="Avoid unnecessary constructors - the compiler will generate these for you"
class="net.sourceforge.pmd.rules.UnnecessaryConstructorRule">
<description>
Unnecessary constructor detects when a constructor is not necessary; i.e., when there's only one constructor,
it's public, has an empty body, and takes no arguments.
</description>
<example>
<![CDATA[
public class Foo {
public Foo() {}
}
]]>
</example>
</rule>
</ruleset>

View File

@ -30,6 +30,7 @@ public class PMD {
try {
JavaParser parser = new JavaParser(reader);
ASTCompilationUnit c = parser.CompilationUnit();
Thread.yield();
//c.dump("");
SymbolFacade stb = new SymbolFacade();
stb.initializeWith(c);

View File

@ -2,7 +2,7 @@
package net.sourceforge.pmd.ast;
public class ASTConstructorDeclaration extends SimpleNode {
public class ASTConstructorDeclaration extends AccessNode {
public ASTConstructorDeclaration(int id) {
super(id);
}

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,55 @@
/*
* User: tom
* Date: Nov 1, 2002
* Time: 8:54:28 AM
*/
package net.sourceforge.pmd.rules;
import net.sourceforge.pmd.AbstractRule;
import net.sourceforge.pmd.RuleContext;
import net.sourceforge.pmd.ast.*;
import java.util.ArrayList;
import java.util.List;
public class UnnecessaryConstructorRule extends AbstractRule {
private List constructors;
public Object visit(ASTCompilationUnit node, Object data) {
constructors = new ArrayList();
node.findChildrenOfType(ASTConstructorDeclaration.class, constructors);
// there must be be the only constructor
// TODO this gets thrown off by inner classes
if (constructors.size() > 1) {
return data;
}
return super.visit(node, data);
}
public Object visit(ASTConstructorDeclaration node, Object data) {
// must be public
AccessNode accessNode = (AccessNode)node;
if (!accessNode.isPublic()) {
return data;
}
// must have no parameters
ASTFormalParameters params = (ASTFormalParameters)accessNode.jjtGetChild(0);
if (params.jjtGetNumChildren() > 0) {
return data;
}
// the constructor must be empty
if (node.jjtGetNumChildren() > 1) {
return data;
}
RuleContext ctx = (RuleContext)data;
ctx.getReport().addRuleViolation(createRuleViolation(ctx, node.getBeginLine()));
return data;
}
}

View File

@ -0,0 +1,3 @@
public class UnnecessaryConstructor1 {
public UnnecessaryConstructor1() {}
}

View File

@ -0,0 +1,3 @@
public class UnnecessaryConstructor2 {
private UnnecessaryConstructor2() {}
}

View File

@ -0,0 +1,3 @@
public class UnnecessaryConstructor3 {
public UnnecessaryConstructor3(int x) {}
}

View File

@ -0,0 +1,5 @@
public class UnnecessaryConstructor4 {
public UnnecessaryConstructor4() {
int x = 2;
}
}