2013-09-23 45 views
7

我有一个新的代码库出现次数的其中存在的方法调用等的序列,静态代码分析仪,在连续的行检测的代码模式

object o = something.foo(); 
bar(o); 
something.foobar(); 

。我想在我的代码中找到/计算这样一个序列的总数,其中对象“某事”的名称可能不同,但我想对待相同。

我想拉出这些作为一种方法,并查看需要重构的所有位置。我该如何去做这样的事情?

+0

我不知道任何工具,可以做到这一点现成的架子。你可以写(或者扩展现有的)findbug插件这样做的检查:http://findbugs.sourceforge.net/ – Jayan

+0

为什么不能简单地搜索在你的IDE正则表达式的模式?应该给你计数和地点... – assylias

+0

@assylias正则表达式可能工作,但我认为这可能是非常困难的。此外,您可能需要应对所有语法细节,可能会在某个地方或其他地方进行投射。 – SpaceTrucker

回答

1

你可以使用正则表达式 - 在Netbeans的,例如,此正则表达式:

(?s)object o = (.*?)\.foo\(\);\s+bar\(o\);\s+(\1)\.foobar\(\); 

找到的所有线,如:

object o = xyz.foo(); 
bar(o); 
xyz.foobar(); 

其中xyz可以是任何东西,只要它是在同一第一行和最后一行。

+0

也许你应该考虑你的正则表达式中的空行和注释行。 – SpaceTrucker

+0

@SpaceTrucker空白行已被该正则表达式忽略。如果需要,评论确实可以添加。 – assylias

+0

要做空白的权利,你需要一堆额外的正则表达式插入到处;同样对于评论。这对于更复杂的模式会变得非常多毛。如果在方法参数括号内有任意的参数表达式(我认为Op的情况并不完全如他所示),正则表达式会让你完全失败,因为它不能可靠地跳过这些表达式。 –

2

Intellij IDEA(包括免费社区版本)重复代码检测&替换。

如果您使用其重构功能将某种出现转化为方法,它会遍历代码库并询问您是否要在其他位置替换它。

1

如果您的代码是Java 1.6或更低版本,则可以使用Eclipse MoDisco来生成Java项目的EMF model实例。然后,您可以实施Model Query来搜索您描述的模式。即使MoDisco Java模型基于Java 1.5,也可以在1.6中使用它,因为在1.6中没有引入语法变更。

2

有些工具可以做到这一点,他们被称为program transformation tools

如果您真的想用DMS规则语言(RSL)将它们识别为连续的行,使用我们的DMS Software Reengineering Toolkit程序转换引擎。 RSL让你写的模式在语言的语言语法,其语法已经知道DMS方面:

domain Java~v7; 

pattern odd_pattern(IDENTIFIER: o, 
        qualifier: something, 
        IDENTIFIER: foo 
        IDENTIFIER: bar, 
        IDENTIFIER: foobar, 
        more: stmt_sequence): stmt_sequence 
= " Object \o = \something.\foo; 
    \bar(\o); 
    \something.\foobar(); 
    \more"; 

这定义在指定的符号(“域名的Java〜V7”的表面语法方面的模式)。每个模式都有一个名称(“odd_pattern”),以便您可以区分多种模式。一个模式具有一组强制(干净语法)语法类别指定的子模式,命名为<(非)终端:名称>。这个模式有几个不同的标识符,模式名称o,foo,bar,foobar。我猜你的意思是某种合格的途径,但也许你的意思是它只是一个标识符。

图案内容在元引号定义区分目标语言的RSL模式语言文本(Java)的图案文字。该元引号内,\巴兹意味着句法类别N其中巴兹的图案可变巴兹在模式参数列表中定义为N:baz 相同发生在多个位置的模式变量需要相同的替换

鉴于此模式,您可以要求DMS在哪里与(Java)AST匹配。通过与AST匹配,解决空白,注释,非标准化字符串/标识符/数字等问题。被淘汰。通过简单的计数匹配,就可以得到OP的原始期望指标。 [我们已经在很大程度上完成了RSL模式的扩展,其中元素通过数据流而不是代码语法连接。

想必他要变换这些情况下进入一些其他的代码,他可以写做,在RSL,

rule rewrite_odd_pattern(parms): stmt_sequence 
     odd_pattern(parms) -> replacement_pattern(parms); 

提一些“replacement_pattern”写类似。

如果OP只有这样的模式数量不多,他可能会更好使用正则表达式或只是猛击,而不是让DMS(或其他程序转换工具),并设置它。如果他这么做了,或者他们分散在一大堆代码中,模式很复杂,或者他有许多类似的事情要做,权衡可能会以另一种方式提出。