在Java中执行RFC计算的算法

时间:2008-08-21 13:50:36

标签: java regex algorithm reflection

Java类的RFC是为了响应消息传递给类的对象或类中的某个方法而调用的所有方法的集合。 RFC = M + R在哪里 M =班级中的方法数量。 R =从M直接调用的其他方法的总数。

Thinking C是.class,J是我们需要计算RFC的.java文件。

class J{

 a(){}
 b(){}
 c(){
   e1.e();
   e1.f();
   e1.g();
 }
 h(){
   i.k();
   i.j();
  }
  m(){}
  n(){
   i.o();
   i.p();
   i.p();
   i.p();
  }
}

这里M = 6 并且R = 9(不要担心在循环内调用。它被认为是单个调用)

计算M很容易。使用类加载器加载C并使用反射来获取方法的数量。

计算R不是直接的。我们需要计算来自类的方法调用的数量。仅限第一级。

为了计算R,我必须使用正则表达式。通常格式是(不使用。的调用不计算)

[variable_name].[method_name]([zero or more parameters]);

[variable_name].[method_name]([zero or more parameters])
当调用return直接成为另一个方法的参数时,带分号的

。 或

[variable_name].[method_name]([zero or more parameters]).method2();

这变成了两个方法调用

您能想到的方法调用的其他模式是什么?除了使用可用于计算R的RegEx之外还有其他方法。


更新
@McDowell 看起来像使用BCEL我可以简化整个过程。让我试一试。

4 个答案:

答案 0 :(得分:2)

您可以将Byte Code Engineering Library与二进制文件一起使用。您可以使用DescendingVisitor访问班级的成员和参考。我已将它用于find class dependencies

或者,您可以重用某些源文件模型。我很确定Eclipse JDT中的Java编辑器是由某种形式的模型支持的。

答案 1 :(得分:0)

您应该在Java language specification

中找到答案

你已经忘记了静态方法调用,在参数内调用方法...

答案 2 :(得分:0)

使用反射调用方法(方法的名称是字符串)。

答案 3 :(得分:0)

M是否包含对自己方法的调用?或者调用内部类?例如:

class J {
  a() { }
  b() { this.a(); }
  c() { jj.aa(); }
  d() { i.k(); }
  e() { this.f().a(); }
  f() { return this; }
  g() { i.m().n(); }

  class JJ {
    aa() { a(); }
  }
}

这个M值是多少?对此类中未定义的方法(d()和g()函数中的调用)只有三个函数调用。您想要包含对内部类的调用,还是要调用内部类中的主类?你想在同一个类中包含对其他方法的调用吗?

如果您正在查看任何方法调用,无论源代码如何,那么正则表达式可能会起作用,但要正确起来会很棘手(正则表达式是否正确地忽略包含方法调用内容的字符串?它是否处理?构造函数调用正确?)。如果您关心方法调用的来源,那么正则表达式可能无法满足您的需求。你需要使用反射(虽然不幸的是我不太了解反射在那里有用)。