0

我正在编写一个应用程序,其目的是优化交易策略。为简单起见,仅假设我们有一个交易策略,即“在此处进入”,然后是“在交易中退出”,然后让我们有两个模型:一个说我们应该承担多少风险(如何如果我们站在市场的错误一边,我们会损失多少),另一个说我们应该获得多少利润(即如果市场同意,我们将获得多少利润)。

为简单起见,我将历史已实现交易称为刻度。这意味着,如果我“在第 28 次交易时输入”,这意味着我将在我的数据集中的第 28 次交易时以该交易的价格输入交易。刻度按时间顺序存储在我的数据集中。

现在,想象一下整个数据集的入口策略有 500 个入口。对于每个条目,我可以预先计算确切的条目刻度。我还可以计算每个入口点的退出策略所确定的退出点(同样作为刻度数)。对于每个条目,我还可以预先计算建模的损失和利润以及这些损失或利润会受到打击的刻度。剩下要做的最后一件事是计算首先会发生什么,即退出策略、退出亏损或退出盈利。

因此,我遍历交易数组并计算 exitTick[i] = min(exitTickByStrat[i], exitTickByLoss[i], exitTickByProfit[i])。整个过程非常缓慢(假设我这样做了 100M 次)。我怀疑缓存未命中是罪魁祸首。问题是:这能以某种方式更快吗?我必须遍历 4 个非平凡长度的数组。我提出的一个建议是将数据分组为四个元组,即具有一组结构,例如(entryTick、exitOnStrat、exitOnLoss、exitOnProfit)。由于更好的缓存可预测性,这可能会更快,但我不能肯定地说。为什么我到目前为止还没有测试它是因为检测分析器在某种程度上不适用于我的应用程序的发布二进制文件,而采样分析器在我看来是不可靠的(我已经尝试过英特尔的分析器)。

所以最后的问题是:这个问题可以做得更快吗?使用发布二进制文件进行内存分析的最佳分析器是什么?我在Win7,VS2010上工作。

编辑:非常感谢大家。我试图尽可能地简化我原来的问题,因此造成了混乱。只是为了确保它的可读性 - 目标意味着设想/实现的利润,止损意味着设想/实现的损失。

优化器是蛮力的。所以,我有一些策略设置(例如指标周期等),然后是最小/最大 breakEvenAfter/breakEvenBy,然后是为您提供止损/目标值的公式。这些公式也是优化的对象。因此,我有一个优化结构,如

for each in params
{
   calculateEntries()
   for each in beSettings
   {
      precalculateBeData()
      for each in targetFormulaSettings
      {
          precalculateTargetsAndRespectiveExitTicks
          for each in stopFormulaSettings
          {
              precalulcateStopsAndRespectiveExitsTicks
              evaluateExitsAndDetermineImprovement()
          }
       }
    }
}

所以我尽可能地预先计算一些东西,只在需要时计算一些东西。在 30 秒中,计算在 evaluateExitsAndDetermineImprovement() 函数中花费了 25 秒,该函数执行我在原始问题中描述的操作,即选择 min(exitOnPattern、exitOnStop、exitOnTarget)。我需要调用函数 100M 次的原因是因为我有 100M 的所有参数组合。但在最后一个 for 循环中,只有 exitOnStops 数组发生变化。如果有帮助,我可以发布一些代码。我感谢所有的评论!

4

3 回答 3

1

我对交易策略了解不多,但我通常会做一些优化。嗯,有很多优化方法。比如,容器类型,使用不同的 min 函数(我认为 boost 的函数比 stl 库中的函数快一些),尝试减少相同的计算等。您还可以通过使用更快的函数来提高速度,或通过重新设计您的算法来进行优化。

对于分析,我在 Win7 x64 下使用 GlowCode,发布版本也可以。

于 2012-10-04T10:39:25.157 回答
0

也许我完全误解了您的系统,但是:
您“预先计算”的是什么以及何时以及为什么要进行100M 次?

我不知道它是否会对您有所帮助,但它可能会显着简化您的系统 - 有两种常见的交易策略:(描述是我的而非官方的)
1)“定点退出” - 当交易发生时,所有退出点都会被计算出来一次,并定期根据市场条件/价格检查它们。
2)“可变点退出” - 当市场移动时,退出点被重新计算(通常是为了锁定更多利润/减少损失)。

在情况 1) 实际计算只发生一次,所以它应该非常
在情况 2) 计算每次都会发生,但它可以通过许多不同的方式进行优化 - 其中之一是您可以存储您的交易以退出索引点,只有得到和重新计算那些接近实际市场情况。

我不确定您指的是哪个缓存未命中?你数据缓存?CPU缓存?

于 2012-10-04T10:25:03.140 回答
0

所以,经过一番工作,我理解了 Alexandre C 的建议。当我运行缓存未命中分析时,我发现在评估Exits() 函数的 15M 调用中,我只有 30K 缓存未命中,因此不能阻碍该函数的性能通过缓存。因此,我不得不“开始相信”VTune 实际上产生了有效的结果,尽管很奇怪。由于 VTune 输出的分析与当前线程的名称不匹配,我决定启动一个新线程。谢谢大家的意见和建议。

于 2012-10-10T19:04:53.567 回答