考虑一个我正在实现使用Akka处理传入任务的系统的场景.我有一个主要角色接收任务并将它们分派给处理任务的一些工作者.
我的第一直觉是通过让调度员为每个传入任务创建一个actor来实现这一点.在worker actor处理任务后,它将停止.
这对我来说似乎是最干净的解决方案,因为它坚持"一个任务,一个角色"的原则.另一个解决方案是重用actor - 但这涉及清理和一些池管理的额外复杂性.
我知道阿卡的演员很便宜.但我想知道是否存在与重复创建和删除演员相关的固有成本.是否存在与Akka用于记录演员的数据结构相关的隐藏成本?
负载应该是每秒数十或数百个任务的量级 - 将其视为生产网络服务器,每个请求创建一个actor.
当然,正确的答案在于根据传入负载的类型对系统进行分析和微调.但我想知道是否有人可以根据自己的经验告诉我一些事情?
后期编辑:
我应该提供有关手头任务的更多细节:
注意:我很欣赏我的问题的替代解决方案,我一定会考虑它们.但是,我还要回答关于在Akka中密集创建和删除演员的主要问题.
我试图找出Haskell的线程(forkIO生成的线程)究竟是如何映射到OS线程的.
我找到的第一个信息来源,
http://www.haskell.org/ghc/docs/latest/html/libraries/base/Control-Concurrent.html#g:11
指定所有轻量级线程实际上都在一个OS线程上运行,并且只有当Haskell线程块具有安全IO操作时,GHC运行时才会生成一个新的OS线程来运行其他Haskell线程,以便IO调用不会阻止整个计划.
第二个信息来源来自这里,
http://www.haskell.org/ghc/docs/7.0.1/html/users_guide/using-smp.html
这清楚地表明Haskell线程以平衡的方式映射到预定义数量的预先创建的OS线程.这或多或少意味着,如果我有80个轻量级线程,并且在运行我的程序时传入选项+ RTS -N 8,那么将创建至少8个OS线程,并且每个这样的线程将运行10个轻量级线程.在具有8个CPU核心的机器上,这意味着大约10个Haskell线程/核心.
第二个信息来源似乎是更准确的一个,我希望GHC运行时在运行使用该-threaded标志编译的程序时会表现出这种确切的行为.
谁能证实这一点?而且,如果第二个版本是正确的,绑定线程的目的是什么 - 使用forkOS生成的 - 它是否仅用于处理使用线程本地数据的本机代码?
我正在使用ARM库将资源文件读入字符串.我正在使用的代码是这样的:
def readResource(reosurceName: String): String = {
val res = for (writer <- managed(new StringWriter);
is <- managed(this.getClass.getClassLoader.getResourceAsStream(resourceName))) yield {
IOUtils.copy(is, writer)
writer.toString
}
res.acquireAndGet(identity)
}
Run Code Online (Sandbox Code Playgroud)
它看起来有点怪我,尤其是最后一部分acquireAndGet的identity.有没有更好的办法 ?
一般的问题是,你将如何使用这种风格来做这样的事情
val x: String=
for (res1 <- managed(...);
res2 <- managed(...);
...
resn <- managed) yield {
f(res1, res2, ..., resn)
}
Run Code Online (Sandbox Code Playgroud)
行为是,如果for comprehension中的操作失败,我希望将异常传播出该方法,并且应该关闭资源.
我在ManagedResource返回的地图上看到了这个地图ExtractableManagedResource,我可以使用该opt方法从中提取结果.flatMap只返回一个ManagedResource.是否有一个原因 ?
我想使用该&str方法slice_shift_char,但在文档中标记为不稳定:
不稳定:等待有关移位和切片的约定,并且可能无法保证chars和/或char_indices迭代器的存在
使用Rust当前的std库,实现此方法的好方法是什么?到目前为止,我有:
fn slice_shift_char(s: &str) -> Option<(char, &str)> {
let mut ixs = s.char_indices();
let next = ixs.next();
match next {
Some((next_pos, ch)) => {
let rest = unsafe {
s.slice_unchecked(next_pos, s.len())
};
Some((ch, rest))
},
None => None
}
}
Run Code Online (Sandbox Code Playgroud)
我想避免打电话给slice_unchecked.我正在使用Rust 1.1.