- iOS/Objective-C 元类和类别
- objective-c - -1001 错误,当 NSURLSession 通过 httpproxy 和/etc/hosts
- java - 使用网络类获取 url 地址
- ios - 推送通知中不播放声音
Assume that there are an unlimited number of workers each of which can complete one task, each of which takes some time. There are also precedence constraints where one task cannot be completed until another is. What is the minimum amount of time needed for each task to be completed while respecting the precedence order?
As an example, lets say you have 3 tasks.
The first task takes 10 units of time to complete, the second takes 5 units of time to complete, and the third takes 6 units of time to complete.
The constraint is that the 2nd task cannot be started until the 3rd task is finished.
Given this, you can conclude that the minimum time needed for all the tasks to be completed while respecting the precedence is 11.
This is because you can do tasks 1 and 3 (which take times 10 and 6 respectively) simultaneously, and after task 3 is finished, you can begin on task 2 (which takes 5 units of time). Thus, all tasks will end at time 11.
Task 1 (10 Units of time) -> Task 3 (6 Units of time) -> Task 2 (5 Units of time)
最佳答案
我假设任务没有循环依赖。因此,任务及其依赖关系可以表示为 有向无环图 (从这里缩写为 dag ),其中任务是顶点,边是 u -> v
表示任务 u
必须在任务之前完成 v
可以开始了。
您的方法在使用拓扑排序来计算任务完成的顺序方面是正确的,因为该图是一个 dag。我看到您有两个主要问题。
min_time_for_tasks(Graph, topological order):
distance <- integer array whose size is number of vertices
set all entries in visited array to negative infinity
maxDist <- 0
for v in topological order:
if distance[v] == negative infinity:
maxDist <- max(maxDist, longest_path(Graph, distance, v))
return maxDist
// computes the longest path from vertex v
longest_path(Graph, distance, v):
maxDist <- 0
for all edges (v,w) outgoing from v:
// vertex w has not been visited
if distance[w] == negative infinity:
longest_path(Graph, distance, w)
// get the longest path among all vertices reachable from v
maxDist <- max(maxDist, distance[w])
distance[v] <- maxDist + time to complete task v
return distance[v]
// This is a modified kahn's algorithm.
// Again, the graph is assumed to be a dag, and we first compute
// the number of incoming edges to every vertex, since Kahn's
// algorithm is dependent on this information.
// This function will return an array of sets of tasks which
// can be done at the same time.
// So all tasks in the set in returnArray[0] can be done at the same
// time, all tasks in the set in returnArray[1] can be done at the
// same time, etc. Explanation will be available after the
// pseudocode
compute_simultaneous_tasks(Graph):
into <- integer array, all entries initialized to 0
// this function is defined below
compute_incoming_edges(Graph, into)
returnArray <- empty array
VSet <- Set of all vertices in the graph
while VSet is not empty:
// retrieve all vertices with no incoming edges
// this means their prerequisite tasks have been completed,
// and we can execute that particular task
headVertices <- all vertices `v` in VSet such that into[v] is 0
// remove all the vertices in headVertices from VSet
VSet <- VSet.remove(headVertices)
// we are going to remove the vertices in headVertices,
// so the edges outgoing from them will be removed as well.
for each vertex v in headVertices:
for each vertex w outgoing from v:
into[w] <- into[w] - 1
// all the vertices in headVertices can be started at the
// same time, since their prerequisite tasks have been
// completed
returnArray.append(headVertices)
return returnArray
// computes the number of edges leading into each vertex
// so into[x] gives the number of edges leading into vertex x
// from some other vertex
compute_incoming_edges(Graph, into):
for each vertex v in Graph:
for each vertex w outgoing from v:
into[w] <- into[w] + 1
compute_simultaneous_tasks
函数将返回一组集合。每个集合包含可以同时完成的顶点/任务。为了了解为什么会这样,在
compute_simultaneous_tasks
的主循环中,我们提取所有没有传入边的顶点。这相当于在没有先决条件的情况下提取所有任务。因此,我们可以看到同时执行这组任务是安全的,因为它们没有先决条件,而且肯定不相互依赖!然后,我们移除它们的出边,以模拟它们的完成。然后我们继续循环的下一次迭代,等等。
while
的每次迭代中循环,我们正在做我们刚刚描述的事情,因此在
returnArray[0]
中执行所有任务是安全的。同时,所有任务在
returnArray[1]
同时
但是 只有在
returnArray[0]
中的所有任务之后已完成,
returnArray[2]
中的所有任务在
returnArray[1]
之后完成,等等。
returnArray[0]
正在第 0 波,
returnArray[1]
是第 1 波,等等。请注意,我们只从波
中删除所有顶点的出边边。后 我们已经提取了所有具有 0 个传入边的顶点。
关于algorithm - 用拓扑排序求调度任务的最短完成时间,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/20864641/
这个问题在这里已经有了答案: Integer summing blues, short += short problem (5 个答案) 关闭 7 年前。 版本:Visual Studio Prof
我尝试执行以下代码: public class Test5 { /** * @param args */ public static void main(String[] args) {
这是我的任务,我尝试仅使用简短的 if 语句来完成此任务,我得到的唯一错误是使用“(0.5<=ratio<2 )”,除此之外,构造正确吗? Scanner scn = new Scanner(
已关闭。此问题需要 debugging details 。目前不接受答案。 编辑问题以包含 desired behavior, a specific problem or error, and the
我有一个简单的类型 data Day = Monday | Tuesday | Wednesday | Thursday | Friday 我是haskell的新手,所以我写==如下。 (==) :
如何实现“简短”和“详细”两个按钮? “短”应该是默认值,并显示页面的一个版本。单击“详细”按钮后,应显示该页面的另一个版本。 由于这有点难以解释,或许可以看下面的例子。 示例页面: 别管内容 需要j
有没有一种方法可以在 C# 中执行此操作,而无需为现有的每个 var 类型创建一个新方法来重载? $box = !empty($toy) : $toy ? ""; 我能想到的唯一方法是: if (t
我想使用 setInterval 创建一个节拍器。我希望能够达到 300 bpm 这样的高 bpm。即使文件足够短,可以根据需要播放多次,它也很容易 打嗝。此外,许多浏览器都存在短音频文件的问题——S
我们现在有一个正在生产中的应用程序,它会将 IAP 收据发送到我们的服务器,这些收据显然太短,而且我们的服务器没有经过 apple 的验证。 Apple 正确验证的长收据长度为 3192。短收据长度均
例如,许多软件使用的许可证 key 。我曾想过对一个序列进行密码签名,所以我可能有 4 个字节用于 ID,8 个字节用于签名,但我找不到合适的算法。 我需要的是攻击者无法轻易生成,但存储在大约 20
作为一个学生项目,我们正在构建一个机器人,它应该跑完规定的路线并捡起一个木制立方体。它的核心是一台运行 debian 的单板计算机,配备 ARM9,频率为 250MHz。因此 Controller 的
在将 short 转换为字节数组时,我在网上找到了以下解决方案,但不太理解所涉及的逻辑。 //buffer is an array of bytes, bytes[] buffer[position]
如何在 PHP namespace 环境中检查对象的类而不指定完整的命名空间类。 例如,假设我有一个对象库/实体/契约(Contract)/名称。 以下代码不起作用,因为 get_class 返回完整
我有一个 View 范围的托管 bean,其托管属性绑定(bind)到查询字符串参数。 JSF 给了我熟悉的异常: javax.faces.FacesException: Property reset
根据 this post我已经修复了对象检查器。有时代码可以很好地运行 10 个条目,使它们全部正确,有时它可以运行 5 个条目。有时它会导致条目错误。 在获取元素的内部文本时总是会失败。当它的 Y/
我正在编写一组工具,其中 C++ 应用程序使用 AES 加密标准对数据进行编码,而 Java 应用程序对其进行解码。据我所知, key 长度必须为 16 个字节。但是当我尝试使用不同长度的密码时,我遇
我有以下代码: short num_short = 1; int possible_new_short = 1; valid = 1; while (valid) { poss
因此,作为 C 的新手,我遇到了我的第一个 SIGSEGV 错误。它出现在一个简短的 C 程序中,该程序旨在成为“猜数字”游戏。它由一个比较两个数字的自定义函数和一个带有输入的 do-while 循环
我不是严格意义上的初级程序员,但我没有接受过数学以外的正规教育 - 所以这纯粹是业余爱好,可能是业余的。 我最近自己开发了一个算法来解决这个问题,但我想知道是否有任何相对简单的算法明显更高效/更快?
我正在使用短条件来区分记录列表中显示的值。 例如,如果我希望强调 ( ) 标识符大于 100 的客户的姓名,请执行以下操作: {# Displays the identifier of the c
我是一名优秀的程序员,十分优秀!