交易VBA循环的对

时间:2015-06-01 22:20:23

标签: excel vba loops trading

当我想使用Excel VBA建立一对交易自动化时,我遇到了问题。

我的策略是当两只股票的点差达到+/- 2标准差时开仓(OTC_Sell或OTC_Buy),并在两只股票的点差达到+/- 4时平仓(CTC_buy或CTC_sell)标准偏差或回击均值。一旦仓位平仓,我可以在收到另一个未平仓交易条件(OTC)后再开仓。

然而,当我运行代码时,似乎循环只运行一次,因为我只能进行一次交易(以黄色突出显示)。在此单元格之后,我只能获得零但没有其他交易信号。我从原始列旁边的那个单元格重新运行代码并获得另一个交易(以绿色突出显示)。但是,之后我得到全零。而我希望在一列内得到所有交易信号。

Function SignalCTC(Price1, Price2, Mean, SD, StopLoss)
Dim i, j, k, m, n, o, p, numRows, numOTC, order, list, flag, finish
numRows = Price1.Rows.Count
Dim SignalColOTC()
ReDim SignalColOTC(numRows, 1)
Dim Price1Col()
ReDim Price1Col(numRows)
Dim Price2Col()
ReDim Price2Col(numRows)
Dim P_Ratio()
ReDim P_Ratio(numRows)
'Loop 1
For i = 1 To numRows
    P_Ratio(i) = Price1(i) / Price2(i)
Next i
UpperLim = Mean + (2 * SD)
LowerLim = Mean - (2 * SD)
Count = 0
flag = 0
For i = 1 To numRows
    If (Count = 0 And (P_Ratio(i) < UpperLim) And (P_Ratio(i) > LowerLim)) Then
    Count = 0
    flag = 0
    SignalColOTC(i, 1) = "Wait&See"
    ElseIf (Count = 0 And (P_Ratio(i) > UpperLim)) Then
        Count = 1
        flag = 1
        SignalColOTC(i, 1) = "Wait&See"
        ElseIf (Count = 0 And (P_Ratio(i) < LowerLim)) Then
            Count = 1
            flag = -1
            SignalColOTC(i, 1) = "Wait&See"
            ElseIf (Count = 1 And flag = 1 And (P_Ratio(i) < UpperLim) And (P_Ratio(i) > Mean)) Then
                Count = 0
                flag = 0
                SignalColOTC(i, 1) = "OTC_Sell"
                ElseIf (Count = 1 And flag = -1 And (P_Ratio(i) > LowerLim) And (P_Ratio(i) < Mean)) Then
                    Count = 0
                    flag = 0
                    SignalColOTC(i, 1) = "OTC_Buy"
                    Else: SignalColOTC(i, 1) = "Wait&See"
    End If
Next i
numOTC = 0
order = 0
list = 0
For i = 1 To numRows
    If (SignalColOTC(i, 1) = "OTC_Sell") Or (SignalColOTC(i, 1) = "OTC_Buy") Then
    numOTC = numOTC + 1
    Else: numOTC = numOTC
    End If
Next i
'Dim x
'Loop 2
    Dim SignalColCTC()
    ReDim SignalColCTC(numRows, numOTC)
    For n = 1 To numRows
        If (SignalColOTC(n, 1) = "OTC_Sell") Then
        list = list + 1
        SignalColCTC(n, list) = "OTC_Sell"
        For j = n + 1 To numRows
            If ((P_Ratio(j) < Mean) Or (Abs(P_Ratio(j)) > (1 + StopLoss) * Abs(P_Ratio(n)))) Then
            SignalColCTC(j, list) = "CTC_Buy"
            Else: SignalColCTC(j, list) = "Wait&See"
            End If
        Next j
        ElseIf (SignalColOTC(n, 1) = "OTC_Buy") Then
            list = list + 1
            SignalColCTC(n, list) = "OTC_Buy"
            For k = n + 1 To numRows
                If ((P_Ratio(k) > Mean) Or (Abs(P_Ratio(k)) < (1 - StopLoss) * Abs(P_Ratio(n)))) Then
                SignalColCTC(k, list) = "CTC_Sell"
                Else: SignalColCTC(k, list) = "Wait&See"
                End If
            Next k
        End If
    Next n
'Loop 3
    For o = 1 To numRows
        For list = 1 To numOTC
            If (SignalColCTC(o, list) = "CTC_Buy") Or (SignalColCTC(o, list) = "CTC_Sell") Then
                For p = o + 1 To numRows
                SignalColCTC(p, list) = "0"
                Next p
            End If
        Next list
    Next o
SignalCTC = SignalColCTC
End Function

这应该是Loop 3的问题吗?我试图将循环2和循环3放在一个循环中,但是我甚至没有一个交易信号,但这次都是零。

 Function SignalCTC(Price1, Price2, Mean, SD, StopLoss)
    Dim i, j, k, m, n, o, p, numRows, numOTC, order, list, flag, finish
    numRows = Price1.Rows.Count
    Dim SignalColOTC()
    ReDim SignalColOTC(numRows, 1)
    Dim Price1Col()
    ReDim Price1Col(numRows)
    Dim Price2Col()
    ReDim Price2Col(numRows)
    Dim P_Ratio()
    ReDim P_Ratio(numRows)
    'Loop 1
    For i = 1 To numRows
        P_Ratio(i) = Price1(i) / Price2(i)
    Next i
    UpperLim = Mean + (2 * SD)
    LowerLim = Mean - (2 * SD)
    Count = 0
    flag = 0
    For i = 1 To numRows
        If (Count = 0 And (P_Ratio(i) < UpperLim) And (P_Ratio(i) > LowerLim)) Then
        Count = 0
        flag = 0
        SignalColOTC(i, 1) = "Wait&See"
        ElseIf (Count = 0 And (P_Ratio(i) > UpperLim)) Then
            Count = 1
            flag = 1
            SignalColOTC(i, 1) = "Wait&See"
            ElseIf (Count = 0 And (P_Ratio(i) < LowerLim)) Then
                Count = 1
                flag = -1
                SignalColOTC(i, 1) = "Wait&See"
                ElseIf (Count = 1 And flag = 1 And (P_Ratio(i) < UpperLim) And (P_Ratio(i) > Mean)) Then
                    Count = 0
                    flag = 0
                    SignalColOTC(i, 1) = "OTC_Sell"
                    ElseIf (Count = 1 And flag = -1 And (P_Ratio(i) > LowerLim) And (P_Ratio(i) < Mean)) Then
                        Count = 0
                        flag = 0
                        SignalColOTC(i, 1) = "OTC_Buy"
                        Else: SignalColOTC(i, 1) = "Wait&See"
        End If
    Next i
    numOTC = 0
    order = 0
    list = 0
    For i = 1 To numRows
        If (SignalColOTC(i, 1) = "OTC_Sell") Or (SignalColOTC(i, 1) = "OTC_Buy") Then
        numOTC = numOTC + 1
        Else: numOTC = numOTC
        End If
    Next i
    'Dim x
    x=1
    For Y=x to numRows
    'Loop 2
        Dim SignalColCTC()
        ReDim SignalColCTC(numRows, numOTC)
        For n = x To numRows
            If (SignalColOTC(n, 1) = "OTC_Sell") Then
            list = list + 1
            SignalColCTC(n, list) = "OTC_Sell"
            For j = n + 1 To numRows
                If ((P_Ratio(j) < Mean) Or (Abs(P_Ratio(j)) > (1 + StopLoss) * Abs(P_Ratio(n)))) Then
                SignalColCTC(j, list) = "CTC_Buy"
                Else: SignalColCTC(j, list) = "Wait&See"
                End If
            Next j
            ElseIf (SignalColOTC(n, 1) = "OTC_Buy") Then
                list = list + 1
                SignalColCTC(n, list) = "OTC_Buy"
                For k = n + 1 To numRows
                    If ((P_Ratio(k) > Mean) Or (Abs(P_Ratio(k)) < (1 - StopLoss) * Abs(P_Ratio(n)))) Then
                    SignalColCTC(k, list) = "CTC_Sell"
                    Else: SignalColCTC(k, list) = "Wait&See"
                    End If
                Next k
            End If
        Next n
    'Loop 3
        For o = x To numRows
            For list = 1 To numOTC
                If (SignalColCTC(o, list) = "CTC_Buy") Or (SignalColCTC(o, list) = "CTC_Sell") Then
                    For p = o + 1 To numRows
                    SignalColCTC(p, list) = "0"
                    Next p
                End If
                x = p
            Next list
        Next o
    Next Y
    SignalCTC = SignalColCTC
    End Function

1 个答案:

答案 0 :(得分:0)

这里有趣的问题。快速查看代码,没有任何内容跳出来。循环3对我来说似乎很好,但无论如何似乎并不重要。

也许你实施的逻辑不是你想要的?我添加了我的评论版本(除标签外没有真正的变化)。可能是一个很好的方法,你做类似检查循环1和2正在做你想要的。

另外,我假设平均值和SD输入是价格比率?为什么不在功能中解决它们?

最后,请确保在将来声明变量时指定数据类型。可以避免错误和混乱。例如'dim i as integer'

Function SignalCTC(Price1, Price2, Mean, SD, StopLoss)

    Dim i, j, k, m, n, o, p, numRows, numOTC, order, list, flag, finish

    numRows = Price1.Rows.Count

    Dim SignalColOTC()
    ReDim SignalColOTC(numRows, 1)
    Dim Price1Col()
    ReDim Price1Col(numRows)
    Dim Price2Col()
    ReDim Price2Col(numRows)
    Dim P_Ratio()
    ReDim P_Ratio(numRows)

    'calculate ratios
    For i = 1 To numRows
        P_Ratio(i) = Price1(i) / Price2(i)
    Next i

    UpperLim = Mean + (2 * SD)
    LowerLim = Mean - (2 * SD)
    Count = 0
    flag = 0

    'Loop 1
    'identify possible opening events
    For i = 1 To numRows
        'if no events (within limits), reset
        If (Count = 0 And (P_Ratio(i) < UpperLim) And (P_Ratio(i) > LowerLim)) Then
            Count = 0
            flag = 0
            SignalColOTC(i, 1) = "Wait&See"
        'if exceeds for the first time
        ElseIf (Count = 0 And (P_Ratio(i) > UpperLim)) Then
            Count = 1
            flag = 1
            SignalColOTC(i, 1) = "Wait&See"
        'if under limit for the first time
        ElseIf (Count = 0 And (P_Ratio(i) < LowerLim)) Then
            Count = 1
            flag = -1
            SignalColOTC(i, 1) = "Wait&See"
        'if already exceeded once and now within limits
        ElseIf (Count = 1 And flag = 1 And (P_Ratio(i) < UpperLim) And (P_Ratio(i) > Mean)) Then
            Count = 0
            flag = 0
            SignalColOTC(i, 1) = "OTC_Sell"
        'if were under limit once and now within limits
        ElseIf (Count = 1 And flag = -1 And (P_Ratio(i) > LowerLim) And (P_Ratio(i) < Mean)) Then
            Count = 0
            flag = 0
            SignalColOTC(i, 1) = "OTC_Buy"
        Else
            SignalColOTC(i, 1) = "Wait&See"
        End If
    Next i

    numOTC = 0
    order = 0
    list = 0

    'count opening events
    For i = 1 To numRows
        If (SignalColOTC(i, 1) = "OTC_Sell") Or (SignalColOTC(i, 1) = "OTC_Buy") Then
            numOTC = numOTC + 1
        Else
            'numOTC = numOTC 'redundant, don't need
        End If
    Next i

    'Loop 2
    'identify closing events
    Dim SignalColCTC()
    ReDim SignalColCTC(numRows, numOTC)

    For n = 1 To numRows
        If (SignalColOTC(n, 1) = "OTC_Sell") Then
            list = list + 1 'scroll to next column
            SignalColCTC(n, list) = "OTC_Sell" 'we know this is the sale event
            For j = n + 1 To numRows 'remaining rows
                'if hits mean, or makes a big loss
                If ((P_Ratio(j) < Mean) Or (Abs(P_Ratio(j)) > (1 + StopLoss) * Abs(P_Ratio(n)))) Then
                    SignalColCTC(j, list) = "CTC_Buy" 'close position
                Else
                    SignalColCTC(j, list) = "Wait&See"
                End If
            Next j
        ElseIf (SignalColOTC(n, 1) = "OTC_Buy") Then 'logic repeated for sale
            list = list + 1
            SignalColCTC(n, list) = "OTC_Buy"
            For k = n + 1 To numRows
                If ((P_Ratio(k) > Mean) Or (Abs(P_Ratio(k)) < (1 - StopLoss) * Abs(P_Ratio(n)))) Then
                    SignalColCTC(k, list) = "CTC_Sell"
                Else
                    SignalColCTC(k, list) = "Wait&See"
                End If
            Next k
        End If
    Next n

    'Loop 3
    'just filling zeros after position is closed
    For o = 1 To numRows
        For list = 1 To numOTC
            If (SignalColCTC(o, list) = "CTC_Buy") Or (SignalColCTC(o, list) = "CTC_Sell") Then
                For p = o + 1 To numRows
                    SignalColCTC(p, list) = "0"
                Next p
            End If
        Next list
    Next o

    SignalCTC = SignalColCTC

End Function

修改

通过这个过程,我希望输出矩阵看起来像:

SignalColCTC:

OTC_Buy     Null        Null
Wait&See    Null        Null
Wait&See    OTC_Sell    Null
Wait&See    Wait&See    Null
CTC_Sell    Wait&See    Null
0           CTC_Buy     OTC_Buy
0           0           Wait&See

(N.B。我认为空值后来变为零)

这对我来说似乎是合理的。也许你想要做的是将对转换成一列?您上传的图片中似乎是您想要的。