就我被告知我需要的方法而言,我已经有了该程序所需的框架。但是,除此之外,我在弄清楚如何开始编写这个程序时遇到了麻烦。详细情况如下。 我不是要求为我完成我的程序,实际上我只是对如何开始感到困惑。我知道我需要读取用户输入来获取文本文件,我们在我的大学使用扫描仪,但我不知道这是否需要在构造函数中、main 中或其他方法中。
接受单个命令行参数 - 即包含行分隔的字符串对列表的文本文件。这些字符串对将表示依赖图中的边。例如,读取为:A.java B.java 的行表示从 A.java 到 B.java 的依赖边。表示上图的文件可能如下所示: Main.java A.java A.java B.java
将从文件中读取的每个字符串映射到唯一的整数标识符。这种映射将使将文件名转换为数组索引变得容易。
将每个唯一整数标识符(从上面)映射回原始字符串。
计算表示字符串之间依赖关系的邻接矩阵。
对邻接矩阵执行传递闭包操作以生成表示字符串之间传递依赖关系的新闭包矩阵。执行此操作的一种简单方法是 Floyd-Warshall 算法 - 您可能想对这个主题进行一些研究。
您的输出必须遵循课程网站上示例输出文件所示的格式。课程网站上有一个示例输入文件和相应的输出文件。在此示例中,您的输出必须具有相同的格式。目标是使输出信息具有有吸引力、可读的格式,清楚地表明下面列出的每个方法都可以正常工作。
具有私有字段返回类型的方法,例如 getNameIdMap、getIdNameMap、getRoots 等,而不是返回我们类的内部状态的可变部分,即应该返回该映射的副本(克隆)列表。这样,调用者就可以得到一个完全可用的对象(例如,列表或地图),而不会影响类的内部状态。
您的程序还应提供以下方法:
public Map getNameIdMap() - 返回从字符串到唯一整数标识符的映射。整数标识符表示给定字符串的邻接矩阵和闭包矩阵的索引。注意:在 Python 中,返回值必须是一个字典,其中键是字符串,值是整数。
public Map getIdNameMap() - 返回从唯一整数标识符到原始字符串的映射。注意:在 Python 中,返回值必须是一个字典,其中键是整数,值是字符串。
public int[][] getDependenceGraph() - 返回表示文件之间依赖关系的邻接矩阵。
public int[][] getTransitiveDependenceGraph() - 在应用传递闭包操作后返回依赖图。
public List getRoots() - 返回一个字符串列表,这些字符串对应于没有其他文件依赖的文件(例如,上面示例中的 Main)。注意:在 Python 中,返回值也是一个字符串列表。
public List getLeaves() - 返回一个字符串列表,这些字符串对应于不依赖其他文件的文件(例如,上例中的 B)。注意:在 Python 中,返回值也是一个字符串列表。
public void removeLeaf(String leaf) - 从邻接和传递闭包矩阵中删除一个叶子。这意味着如果 X 依赖于 Y 并且 Y 是被移除的叶子,那么 X 对 Y 的依赖也会被消除。这可能会或可能不会使 X 成为新的叶子。考虑在矩阵中使用一个特殊的数字(即,除了 0 和 1)来表示该文件已被逻辑删除。
public List firewall(String node) - 计算指定文件的“类防火墙”。在软件工程中,类防火墙概念指出,当对系统进行维护时,只有更改的类和受更改影响的类需要重新测试。注意:在 Python 中,返回值也是一个字符串列表。对于此方法,您应该重新测试间接和直接受影响的类。例如,如果 A 类依赖于 B 类,B 类依赖于 C 类,而你更改了 C 类,那么你应该重新测试 A 类和 B 类。
public void printParallelGroups() - 假设我们想要并行编译文件,我们需要识别不会触发其他文件编译的文件;这些是依赖图中的叶子。此方法识别可以并行编译的文件,打印该文件列表,并将它们从图中删除。该方法应重复此过程,直到所有文件都已“编译”。