使用Scala/Akka实现JVM中的高频交易

kyks70gy  于 2022-11-05  发布在  Scala
关注(0)|答案(4)|浏览(180)

让我们想象一个假设的Java HFT系统,它需要(非常)低的延迟,有许多短暂的小对象(某种程度上是由于不变性(Scala?)),每秒有数千个连接,在事件驱动的架构中有大量消息传递(akka和amqp?)。
对于那些Maven来说,什么样的(假设)是JVM 7的最佳调优?什么类型的代码会让它满意?Scala和Akka会为这种系统做好准备吗?

  • 注意:* 有一些类似的问题,比如one,但是我还没有找到涉及Scala的问题(它在JVM中有自己独特的足迹)。
7lrncoxx

7lrncoxx1#

在Java中可以实现非常好的性能。但是,这个问题需要更具体一些,才能提供一个可信的答案。延迟的主要来源将来自下面的非详尽列表:
1.您创建了多少垃圾,以及GC收集和提升垃圾的工作。根据我的经验,不可变的设计并不适合低延迟。GC调优需要成为一个重点。
1.预热JVM,以便加载类,并且JIT有时间完成其工作。
1.时间复杂度O(1),时间复杂度O(log2),时间复杂度O(log2)。
1.您的设计需要是无锁的,并遵循“Single Writer Principle“。
1.需要付出巨大的努力来理解整个堆栈,并在其使用中表现出机械的同情。
1.设计您的算法和数据结构,使其对高速缓存友好。高速缓存未命中现在是最大的代价。这与进程关联性密切相关,如果设置不正确,可能会导致严重的高速缓存污染。这将涉及对操作系统的同情,甚至在某些情况下涉及一些JNI代码。
1.确保您有足够的内核,以便任何需要运行的线程都有可用的内核,而无需等待。
我最近在博客上写了这样一个练习的case study

afdcj2ne

afdcj2ne2#

在我的笔记本电脑上,Akka 2.3.7参与者之间ping消息的平均延迟约为300 ns,这比由于JVM上的GC暂停而预期的延迟要少得多。
Akka和其他参与者在英特尔酷睿i7- 2640 M here上的代码(包括JVM选项)和测试结果。
P.S.您可以在Dmitry Vyukov的site和Martin Thompson的blog中找到许多低延迟计算的原则和提示。

o2rvlv0m

o2rvlv0m3#

您可能会发现,使用环形缓冲区传递消息将超过Akka所能做的。人们在JVM上为金融应用程序使用的主要环形缓冲区实现是一个称为Disruptor的实现,它经过仔细调整以提高效率(两倍大小的幂)、适合JVM(没有GC,没有锁)和适合现代CPU(没有缓存行的错误共享)。
这是一个从ScalaAngular 的介绍演示http://scala-phase.org/talks/jamie-allen-sdisruptor/index.html#1,最后一张幻灯片上有指向原始LMAX内容的链接。

zlhcx6iw

zlhcx6iw4#

有很多用Java编写的HFT系统,但是我从来没有听说过一个用Scala编写的。为什么?

  1. JVM语言,垃圾收集器是一个常见的地方,并不是HFT的绝对好的选择。但是Java是一个垃圾收集语言。那么,技巧是什么呢?技巧是人们用Java编写HFT就像他们用C一样,我的意思是:他们通过更高的内存分配控制来交换Java提供的一些细节,技巧基本上是用内存中预分配的普通数组或其他一些创造性的解决方案来替换JCF(Java集合框架)。
  2. Scala是一种函数式编程语言,它促进了函数式编程技术的大量使用,其中大多数都由集合框架支持。如果您要摆脱集合框架(通过上面的第1条),那么您基本上没有使用Scala中构建的FP的基本构建块。如果您一开始就没有这样做,那么使用Scala还有什么意义呢?
  3. Akka看起来不是一个好的选择,因为......它是用Scala编写的。所以,除了第(1)项和第(2)项之外,我们也可以排除Akka。
    重点是:自从2012年这个问题被提出以来,技术不断发展。我的答案是现在10年后的未来。我们有远比C或C++更有趣的选择,这是2012年唯一可能的选择。
    好吧......也许不是选项(复数)......但有一个选项:生 rust 了。
    Rust不是一种垃圾收集语言,它是一种安全的编程语言,它是高效的,它提供了一个丰富的异步库,而且它非常快。
    Rust的唯一“问题”是,大银行和金融机构中负责技术指导的人通常都不喜欢创新,更喜欢他们在漫长的职业生涯开始时就已经知道的东西。因此,简而言之,我们需要一段时间才能看到Rust编写的高频交易系统。

相关问题