按 类 信息设置过滤

Filtering set by classes information

假设我想从一些 OFG g 中获取所有字段,同时忽略像 |java+field:///java/lang/System/err| 这样的字段。如何检查结果字段是否实际引用导入项目中的某些 class?

我的尝试是这样的。这里编译器在 <- classes 点亮。所以它不允许from.path。我认为应该可以。

g = buildGraph(createOFG(|project://eLib|));
m = createM3FromEclipseProject(|project://eLib|);
set[str] classes = { cl.path | cl <- classes(m) };
set[loc] fields = { from | <from,_> <- g, 
                       from.scheme == "java+field", from.path <- classes };

我怎样才能完成这项工作?

简单回答:from.path 不是模式语法,因此您可以使用变量代替:

 set[loc] fields = { from | <from,_> <- g, 
                   from.scheme == "java+field", x <- classes, x == from.path };

 set[loc] fields = { from | <from,_> <- g, 
                   from.scheme == "java+field", x := from.path, x <- classes };

这个问题的一个很好的解决方案可能是使用包含关系 m@containment,如果你传递关闭它 m@containment* 并从顶部查询你知道项目中是否有东西,比如 myField in m@containment*[ |java+package:///elib|]

最好将 m@containment*[ |java+package:///elib|] 保留在一个变量中,因为它是一项昂贵的计算。

你可以这样找出包含关系的顶部是怎样的:

rascal> import analysis::graphs::Graph; // or import Graphs; in older versions
ok
rascal> top(m@containment)
set[loc]: {
   |java+package:///org|,
   |java+package:///vinju|
}