martedì 24 maggio 2016

Strategie di Trading

Nel calcolo del PNL ho aggiunto anche la passegiata aleatoria e il moto Browniano geometrico usati nell’esonero 2.
Il poter disporre di un modello che descriva adeguatamente l'andamento dei prezzi azionari risulta particolarmente interessante.

I prezzi dei titoli azionari sono assimilabili a una variabile il cui valore cambia nel tempo in modo aleatorio e in quanto tali sono regolati da un processo aleatorio.
I modelli finanziari più utilizzati si basano sull'ipotesi che la dinamica dei prezzi sia regolata da un processo stocastico continuo a parametro continuo.
Nel nostro esercizio abbiamo utilizzato due tipi di modelli che descrivono l’andamento dei prezzi azionari:

  • Il moto browniano geometrico riflette la natura del prezzo di un'attività finanziaria in quanto una quantità che segue un moto browniano geometrico può assumere soltanto valori maggiori di zero. Questo processo stocastico è stato proposto da Wiener per descrivere matematicamente il movimento di un granellino di polvere sospeso su una superficie d'acqua, movimento causato dai continui bombardamenti delle molecole circostanti.
        Il GBM è un’applicazione della normale. I paramentri sono denominati:
-Drift  = direzione ( media )
-Volatility = volatilità ( varianza )
  • Una random walk invece è un percorso dove ogni passo ha una direzione casuale e possibilmente anche una dimensione casuale. Queste passeggiate aleatorie servono come modelli per studiare fenomeni variabili come la diffusione, il prezzo di attività finanziarie, ecc..
Per generare i prezzi nella random walk usiamo la variabile bernoulliana.
Questo tipo di percorso però non è considerato un modello adatto per generare i prezzi perché se si genera un numero di prezzi sufficientemente elevato si possono ottenere anche valori negativi, e ovviamente per i prezzi questo non è realistico.
Cos’è una strategia di trading? 
Con il termine “sistema di trading”, ci si riferisce a una metodologia rigorosamente definita, che utilizza determinate regole per decidere quando comprare o quando vendere su un certo mercato. Lo scopo del sistema di trading è quello di generare una strategia che sia nel medio lungo periodo profittevole per l’investitore.
E’ importante sottolineare che un sistema di trading non è uno strumento previsivo. Si può pensare ad esso come al lancio di una moneta: 50% di probabilità di vincita e 50% di probabilità di perdita. Se però il sistema fosse studiato in modo tale da produrre nel tempo, e sulla base di un suo uso ripetuto, perdite limitate e vincite ampie, il risultato nel medio-lungo periodo risulterebbe interessante. In ogni caso, il sistema non avrebbe alcuna capacità previsiva anche se risultasse profittevole. Da questa considerazione discende un importante verità del trading: per guadagnare è sufficiente, ma non necessario, prevedere l’andamento futuro dei prezzi.
Un trading plan quindi è l’insieme di una serie di regole che definiscono il “come” e il “quando” un trader piazzerà i propri ordini. Un trading plan, dunque, si compone di elementi che descrivono l’attività di un trader. Ai trader non è imposto alcun limite sulla tipologia di mercato sul quale operare; la cosa importante,però, è che gli strumenti utilizzati per creare la strategia godano di buona liquidità e volatilità.
La liquidità descrive l’abilità di eseguire ordini, cioè è relativo alla facilità con la quale i titoli possono essere acquistati e venduti.
La liquidità si misura in termini di:
  • Ampiezza: quant’è stretto lo spread bid/ask
    [Nota: cosa è lo spread bid/ask? E’ la differenza tra il prezzo bid (denaro) e il prezzo ask (lettera) praticato da un commerciante. Il prezzo bid è il prezzo al quale il negoziante è disposto ad acquistare uno strumento finanziario. Il prezzo ask è quello al quale il negoziante è disposto a vendere uno strumento finanziario.]
  • Profondità: quant’è profondo il mercato, cioè quanti ordini rimangono fuori dal best price
  • Immediatezza: quanto velocemente può essere eseguito un grande ordine
  • Elasticità: quanto impiega il mercato a tornare indietro dopo l’esecuzione di un ordine molto grande
I mercati che godono di buona liquidità tendono ad avere piccoli spread bid/ask e una buona profondità perché i trade vengano eseguiti velocemente. La liquidità è un fattore estremamente importante per i trader perché assicura che gli ordini vengano completati e senza imponenti variazioni di prezzo.
La volatilità, invece, misura la quantità e la velocità con la quale il prezzo di un mercato si muove al rialzo, o al ribasso. La volatilità è spesso vista come un’opportunità di trarre profitto dal cambiamento di prezzo. Qualsiasi cambiamento di prezzo crea un’opportunità di guadagno: sia esso un aumento in fase di uptrend, o un calo in fase di downtrend. Diversamente, se il prezzo rimane invariato è difficile trarre profitto.
Il codice seguente, realizzato in VB.NET, implementa una strategia di trading basata sulle Bande di Bollinger. Dal punto di vista operativo, le Bande di Bollinger danno segnali di acquisto o vendita a seconda se la serie dei prezzi incontra la banda inferiore o superiore. Dal momento che la serie storica tocca la bande inferiore abbiamo un segnale di acquisto; viceversa quando incontra quella superiore il segnale sarà di vendita.


Codice:
Public Class Form1

    Public B As Bitmap
    Public g As Graphics

    Public r As New Rectangle(20, 20, 300, 250)
    Public xiniziale As Integer
    Public yiniziale As Integer
    Public AltezzaIniziale As Integer
    Public LarghezzaIniziale As Integer
    Public rxiniziale As Integer
    Public ryiniziale As Integer
    Public draggingMove As Boolean = False
    Public dx As Integer
    Public dy As Integer


    Public Ran As New Random
    Public serieStorica As New List(Of Class1)
    Public PrezIniziale As Decimal = 100
    Public inizialeInstant As Date = Now
    Public Incremento As Decimal = 1

    Public listSerieStorica As New List(Of PointF)
    Public SerieAvg As New List(Of PointF)
    Public SerieAvgMobile As New List(Of PointF)
    Public SerieDeviazioneSup As New List(Of PointF)
    Public SerieDeviazioneInf As New List(Of PointF)
    Public Sell As New List(Of Double)
    Public Buy As New List(Of Double)
    Public SerieSell As New List(Of PointF)
    Public SerieBuy As New List(Of PointF)

    Public PSs As New List(Of PointF)
    Public PAvg As New List(Of PointF)
    Public PAvgMobile As New List(Of PointF)
    Public PDeviazioneSup As New List(Of PointF)
    Public PDeviazioneInf As New List(Of PointF)
    Public PSell As New List(Of PointF)
    Public PBuy As New List(Of PointF)


    Public maxX As Double
    Public minX As Double
    Public maxY As Double
    Public minY As Double

    Public xt As Integer
    Public yt As Integer


   
    Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click

        'Ogni volta che viene premuto button resettiamo gli oggetti
        Me.listSerieStorica.Clear()
        Me.SerieAvg.Clear()
        Me.SerieAvgMobile.Clear()
        Me.SerieDeviazioneSup.Clear()
        Me.SerieDeviazioneInf.Clear()
        Me.SerieSell.Clear()
        Me.SerieBuy.Clear()

        Dim PrezCorrente As Decimal = PrezIniziale
        Dim correnteInstant As Date = inizialeInstant
        Dim AvgIniziale As Double = PrezIniziale
        Dim AvgCorrente As Double = AvgIniziale
        Dim AvgCorrenteMobile As Double = AvgIniziale
        Dim k As Integer = 12
        Dim varianza As Double = 0
        Dim Deviazione As Double = 0
        Dim DeviazioneSup As Double = AvgIniziale
        Dim DeviazioneInf As Double = AvgIniziale
        Dim ListaK As New List(Of Decimal)

        'Ciclo FOR per la passeggiata aleatoria dei prezzi nel quale vengono definite la serie storica dei prezzi,
        'la media, la media mobile per la Banda di Bollinger.

        For i = 1 To 1000
            Dim Osservazione As New Class1(correnteInstant, PrezCorrente, AvgCorrente, AvgCorrenteMobile, varianza, Deviazione, DeviazioneSup, DeviazioneInf)
            serieStorica.Add(Osservazione)

            If Ran.NextDouble < 0.5 Then
                PrezCorrente = PrezCorrente + Incremento
            Else
                PrezCorrente = PrezCorrente - Incremento
            End If

            correnteInstant = correnteInstant.AddSeconds(1)
            AvgCorrente = ((i - 1) * AvgCorrente + PrezCorrente) / i
            ListaK.Add(PrezCorrente)

            If i <= k Then
                AvgCorrenteMobile = AvgCorrente
            Else
                AvgCorrenteMobile = ((k * AvgCorrenteMobile) + PrezCorrente - ListaK(0)) / k
                ListaK.RemoveAt(0)
            End If

            varianza = ((i - 1) * varianza + (PrezCorrente - AvgCorrente) * (PrezCorrente - AvgCorrenteMobile)) / i
            Deviazione = Math.Sqrt(varianza)
            DeviazioneSup = AvgCorrenteMobile + Deviazione * NumericUpDown1.Value
            DeviazioneInf = AvgCorrenteMobile - Deviazione * NumericUpDown1.Value
        Next

        'Creazione della lista di punti per Bitmap della serie storica, media, media mobile, deviazione superiore, deviazione inferiore.

        listSerieStorica = New List(Of PointF)
        For Each Osservazione As Class1 In serieStorica
            Dim x As Integer
            Dim y As Integer
            y = r.Height - Osservazione.prezzo
            x = Osservazione.istante.Subtract(inizialeInstant).TotalSeconds
            Dim punto As New PointF(x, y)
            listSerieStorica.Add(punto)
        Next

        SerieAvg = New List(Of PointF)
        For Each Osservazione As Class1 In serieStorica
            Dim x As Integer
            Dim y As Integer
            y = r.Height - Osservazione.Avg
            x = Osservazione.istante.Subtract(inizialeInstant).TotalSeconds
            Dim punto1 As New PointF(x, y)
            SerieAvg.Add(punto1)
        Next

        SerieAvgMobile = New List(Of PointF)
        For Each Osservazione As Class1 In serieStorica
            Dim x As Integer
            Dim y As Integer
            y = r.Height - Osservazione.AvgMobile
            x = Osservazione.istante.Subtract(inizialeInstant).TotalSeconds
            Dim punto2 As New PointF(x, y)
            SerieAvgMobile.Add(punto2)
        Next

        SerieDeviazioneSup = New List(Of PointF)
        For Each Osservazione As Class1 In serieStorica
            Dim x As Integer
            Dim y As Integer
            y = r.Height - Osservazione.DeviazioneSup
            x = Osservazione.istante.Subtract(inizialeInstant).TotalSeconds
            Dim punto3 As New PointF(x, y)
            SerieDeviazioneSup.Add(punto3)
        Next

        SerieDeviazioneInf = New List(Of PointF)
        For Each Osservazione As Class1 In serieStorica
            Dim x As Integer
            Dim y As Integer
            y = r.Height - Osservazione.DeviazioneInf
            x = Osservazione.istante.Subtract(inizialeInstant).TotalSeconds
            Dim punto4 As New PointF(x, y)
            SerieDeviazioneInf.Add(punto4)
        Next


        Sell = New List(Of Double)
        Buy = New List(Of Double)
        SerieSell = New List(Of PointF)
        SerieBuy = New List(Of PointF)
        For Each Osservazione As Class1 In serieStorica
            Dim xs As Integer
            Dim ys As Integer
            Dim xb As Integer
            Dim yb As Integer
          
            If Osservazione.prezzo > Osservazione.DeviazioneSup Then
                ys = r.Height - Osservazione.DeviazioneSup
                xs = Osservazione.istante.Subtract(inizialeInstant).TotalSeconds
                Dim punto5 As New PointF(xs, ys)
                SerieSell.Add(punto5)
                Sell.Add(ys)
            ElseIf Osservazione.prezzo < Osservazione.DeviazioneInf Then
                yb = r.Height - Osservazione.DeviazioneInf
                xb = Osservazione.istante.Subtract(inizialeInstant).TotalSeconds
                Dim punto6 As New PointF(xb, yb)
                SerieBuy.Add(punto6)
                Buy.Add(yb)
            End If
        Next

        'Calcolo le coordinate reali della serie storica dei prezzi
        maxX = Double.MinValue
        minX = Double.MaxValue
        maxY = Double.MinValue
        minY = Double.MaxValue
        For Each punto As PointF In listSerieStorica
            If punto.X > maxX Then maxX = punto.X
            If punto.Y > maxY Then maxY = punto.Y
            If punto.X < minX Then minX = punto.X
            If punto.Y < minY Then minY = punto.Y
        Next

        B = New Bitmap(PictureBox1.Width, PictureBox1.Height)
        g = Graphics.FromImage(B)

        'Costruzione di una nuovi listi dei punti che vengono trasformati per rappresentare in Bitmap
        'e potere trascrivere all'interno del rectangolo

        PSs = New List(Of PointF)
        For Each punto As PointF In listSerieStorica
            xt = r.Left + (punto.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto.Y - minY) / (maxY - minY) * r.Height
            PSs.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        PAvg = New List(Of PointF)
        For Each punto1 As PointF In SerieAvg
            xt = r.Left + (punto1.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto1.Y - minY) / (maxY - minY) * r.Height
            PAvg.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        PAvgMobile = New List(Of PointF)
        For Each punto2 As PointF In SerieAvgMobile
            xt = r.Left + (punto2.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto2.Y - minY) / (maxY - minY) * r.Height
            PAvgMobile.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        PDeviazioneSup = New List(Of PointF)
        For Each punto3 As PointF In SerieDeviazioneSup
            xt = r.Left + (punto3.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto3.Y - minY) / (maxY - minY) * r.Height
            PDeviazioneSup.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        PDeviazioneInf = New List(Of PointF)
        For Each punto4 As PointF In SerieDeviazioneInf
            xt = r.Left + (punto4.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto4.Y - minY) / (maxY - minY) * r.Height
            PDeviazioneInf.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        PSell = New List(Of PointF)
        For Each punto5 As PointF In SerieSell
            xt = r.Left + (punto5.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto5.Y - minY) / (maxY - minY) * r.Height
            PSell.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        PBuy = New List(Of PointF)
        For Each punto6 As PointF In SerieBuy
            xt = r.Left + (punto6.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto6.Y - minY) / (maxY - minY) * r.Height
            PBuy.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        'Ciclo FOR per ottenere il beneficio. Questo ciclo ci dà tutte le transazioni con il proffito
        ' e proffito percentuale positiva
        Dim profit As Double = 0
        Dim Pprof As Double = 0
        For i As Integer = 0 To Buy.Count - 1
            For j As Integer = 0 To Sell.Count - 1
                profit = ((Sell(j)) - (Buy(i))) * Buy.Count
                Pprof = (profit / Buy(i)) * 100
                If profit > 0 Then
                    RichTextBox1.AppendText(vbCrLf & "Buy" & "       " & "Sell" & "       " & "Profit" & "           " & "%")
                    RichTextBox1.AppendText(vbCrLf & Buy(i).ToString("#.##").PadLeft(7) & Sell(j).ToString("#.##").PadLeft(7) & profit.ToString("#.##").PadLeft(8) & Pprof.ToString("#.##").PadLeft(13))
                End If
            Next
        Next


        g.Clear(Color.White)

        g.DrawLines(Pens.Black, PSs.ToArray)
        g.DrawLines(Pens.GreenYellow, PAvg.ToArray)
        g.DrawLines(Pens.Gold, PAvgMobile.ToArray)
        g.DrawLines(Pens.Blue, PDeviazioneSup.ToArray)
        g.DrawLines(Pens.Blue, PDeviazioneInf.ToArray)

        elipse()
        g.DrawRectangle(Pens.Black, r)
        PictureBox1.Image = B

        Dim drawFont2 As New Font("Arial", 12, FontStyle.Bold)
        g.DrawString("TRADING GRAPHIC", drawFont2, Brushes.Black, 300, 10)
    End Sub

    'Funzione MouseDown farvi sapere quale pulsante è stato premuto i la posizione all'interno del controllo
    Private Sub PictureBox1_MouseDown(ByVal sender As Object, ByVal e As System.Windows.Forms.MouseEventArgs) Handles PictureBox1.MouseDown
  

        'Contains() determina se un elemento è contenuto nella lista.
        If Not r.Contains(e.X, e.Y) Then Exit Sub
        If e.Button = Windows.Forms.MouseButtons.Left Then
            'la mano Cursor in genere indica che il puntatore si trova sopra un collegamento
            'modificare il cursore del mouse
            Cursor = Cursors.Hand
        ElseIf e.Button = Windows.Forms.MouseButtons.Right Then
            'Ottiene un nord-ovest a due picchi o verso sud-est il ridimensionamento Cursor
            'modificare il cursore del mouse
            Cursor = Cursors.SizeNWSE
        End If

        'Salvare posizione corrente del mouse e del rettangolo
        xiniziale = e.X
        yiniziale = e.Y
        rxiniziale = r.X
        ryiniziale = r.Y
        LarghezzaIniziale = r.Width
        AltezzaIniziale = r.Height

        'abilitare il flag
        draggingMove = True

    End Sub

    'La funzione MouseMove ci permette di modificare la posizione di rectangolo
    Private Sub PictureBox1_MouseMove(ByVal sender As Object, ByVal e As System.Windows.Forms.MouseEventArgs) Handles PictureBox1.MouseMove

   
        If Not draggingMove Then Exit Sub

        'Aggiorniamo le nuove coordinate del rettangolo
        dx = e.X - xiniziale
        dy = e.Y - yiniziale

        'condicione If per modificare le coordinate
        If e.Button = Windows.Forms.MouseButtons.Left Then
            'Se il pulsante sinistro del mouse è stato premuto applico al nuovo vertice del rettangolo
            r.X = rxiniziale + dx
            r.Y = ryiniziale + dy
        Else
            'Modifichiamo l'altezza e la larghezza
            r.Width = LarghezzaIniziale + dx
            r.Height = AltezzaIniziale + dy

        End If

        r = New Rectangle(r.X, r.Y, r.Width, r.Height)


        PSs = New List(Of PointF)
        For Each punto As PointF In listSerieStorica
            xt = r.Left + (punto.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto.Y - minY) / (maxY - minY) * r.Height
            PSs.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        PAvg = New List(Of PointF)
        For Each punto1 As PointF In SerieAvg
            xt = r.Left + (punto1.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto1.Y - minY) / (maxY - minY) * r.Height
            PAvg.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        PAvgMobile = New List(Of PointF)
        For Each punto2 As PointF In SerieAvgMobile
            xt = r.Left + (punto2.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto2.Y - minY) / (maxY - minY) * r.Height
            PAvgMobile.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        PDeviazioneSup = New List(Of PointF)
        For Each punto3 As PointF In SerieDeviazioneSup
            xt = r.Left + (punto3.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto3.Y - minY) / (maxY - minY) * r.Height
            PDeviazioneSup.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        PDeviazioneInf = New List(Of PointF)
        For Each punto4 As PointF In SerieDeviazioneInf
            xt = r.Left + (punto4.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto4.Y - minY) / (maxY - minY) * r.Height
            PDeviazioneInf.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        PSell = New List(Of PointF)
        For Each punto5 As PointF In SerieSell
            xt = r.Left + (punto5.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto5.Y - minY) / (maxY - minY) * r.Height
            PSell.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        PBuy = New List(Of PointF)
        For Each punto6 As PointF In SerieBuy
            xt = r.Left + (punto6.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto6.Y - minY) / (maxY - minY) * r.Height
            PBuy.Add(New PointF(CSng(xt), CSng(yt)))
        Next




        g.Clear(Color.White)

        g.DrawLines(Pens.Black, PSs.ToArray)
        g.DrawLines(Pens.GreenYellow, PAvg.ToArray)
        g.DrawLines(Pens.Gold, PAvgMobile.ToArray)
        g.DrawLines(Pens.Blue, PDeviazioneSup.ToArray)
        g.DrawLines(Pens.Blue, PDeviazioneInf.ToArray)

        g.DrawRectangle(Pens.Black, r)
        PictureBox1.Image = B
        elipse()
        Dim drawFont2 As New Font("Arial", 12, FontStyle.Bold)
        g.DrawString("TRADING GRAPHIC", drawFont2, Brushes.Black, 300, 10)


    End Sub

    'Funzione MouseUp ci permette di trarre il rectangolo quando il pulsante del mouse viene rilasciato
    Private Sub PictureBox1_MouseUp(ByVal sender As Object, ByVal e As System.Windows.Forms.MouseEventArgs) Handles PictureBox1.MouseUp

        'flag per spostare il controllo
        draggingMove = False

        'modificare il cursore
        Cursor = Cursors.Default


    End Sub

    Private Sub elipse()
        For Each punto As PointF In PSell
            g.DrawEllipse(Pens.Red, punto.X, punto.Y, 9, 9)
        Next
        For Each punto As PointF In PBuy
            g.DrawEllipse(Pens.Green, punto.X, punto.Y, 9, 9)
        Next
    End Sub
    Private Sub NumericUpDown1_ValueChanged(ByVal sender As Object, ByVal e As System.EventArgs) Handles NumericUpDown1.ValueChanged


    End Sub

    Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load

    End Sub

End Class

Public Class Form1

    Public B As Bitmap
    Public g As Graphics

    Public r As New Rectangle(20, 20, 300, 250)
    Public xiniziale As Integer
    Public yiniziale As Integer
    Public AltezzaIniziale As Integer
    Public LarghezzaIniziale As Integer
    Public rxiniziale As Integer
    Public ryiniziale As Integer
    Public draggingMove As Boolean = False
    Public dx As Integer
    Public dy As Integer


    Public Ran As New Random
    Public serieStorica As New List(Of Class1)
    Public PrezIniziale As Decimal = 100
    Public inizialeInstant As Date = Now
    Public Incremento As Decimal = 1

    Public listSerieStorica As New List(Of PointF)
    Public SerieAvg As New List(Of PointF)
    Public SerieAvgMobile As New List(Of PointF)
    Public SerieDeviazioneSup As New List(Of PointF)
    Public SerieDeviazioneInf As New List(Of PointF)
    Public Sell As New List(Of Double)
    Public Buy As New List(Of Double)
    Public SerieSell As New List(Of PointF)
    Public SerieBuy As New List(Of PointF)

    Public PSs As New List(Of PointF)
    Public PAvg As New List(Of PointF)
    Public PAvgMobile As New List(Of PointF)
    Public PDeviazioneSup As New List(Of PointF)
    Public PDeviazioneInf As New List(Of PointF)
    Public PSell As New List(Of PointF)
    Public PBuy As New List(Of PointF)


    Public maxX As Double
    Public minX As Double
    Public maxY As Double
    Public minY As Double

    Public xt As Integer
    Public yt As Integer


   
    Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click

        'Ogni volta che viene premuto button resettiamo gli oggetti
        Me.listSerieStorica.Clear()
        Me.SerieAvg.Clear()
        Me.SerieAvgMobile.Clear()
        Me.SerieDeviazioneSup.Clear()
        Me.SerieDeviazioneInf.Clear()
        Me.SerieSell.Clear()
        Me.SerieBuy.Clear()

        Dim PrezCorrente As Decimal = PrezIniziale
        Dim correnteInstant As Date = inizialeInstant
        Dim AvgIniziale As Double = PrezIniziale
        Dim AvgCorrente As Double = AvgIniziale
        Dim AvgCorrenteMobile As Double = AvgIniziale
        Dim k As Integer = 12
        Dim varianza As Double = 0
        Dim Deviazione As Double = 0
        Dim DeviazioneSup As Double = AvgIniziale
        Dim DeviazioneInf As Double = AvgIniziale
        Dim ListaK As New List(Of Decimal)

        'Ciclo FOR per la passeggiata aleatoria dei prezzi nel quale vengono definite la serie storica dei prezzi,
        'la media, la media mobile per la Banda di Bollinger.

        For i = 1 To 1000
            Dim Osservazione As New Class1(correnteInstant, PrezCorrente, AvgCorrente, AvgCorrenteMobile, varianza, Deviazione, DeviazioneSup, DeviazioneInf)
            serieStorica.Add(Osservazione)

            If Ran.NextDouble < 0.5 Then
                PrezCorrente = PrezCorrente + Incremento
            Else
                PrezCorrente = PrezCorrente - Incremento
            End If

            correnteInstant = correnteInstant.AddSeconds(1)
            AvgCorrente = ((i - 1) * AvgCorrente + PrezCorrente) / i
            ListaK.Add(PrezCorrente)

            If i <= k Then
                AvgCorrenteMobile = AvgCorrente
            Else
                AvgCorrenteMobile = ((k * AvgCorrenteMobile) + PrezCorrente - ListaK(0)) / k
                ListaK.RemoveAt(0)
            End If

            varianza = ((i - 1) * varianza + (PrezCorrente - AvgCorrente) * (PrezCorrente - AvgCorrenteMobile)) / i
            Deviazione = Math.Sqrt(varianza)
            DeviazioneSup = AvgCorrenteMobile + Deviazione * NumericUpDown1.Value
            DeviazioneInf = AvgCorrenteMobile - Deviazione * NumericUpDown1.Value
        Next

        'Creazione della lista di punti per Bitmap della serie storica, media, media mobile, deviazione superiore, deviazione inferiore.

        listSerieStorica = New List(Of PointF)
        For Each Osservazione As Class1 In serieStorica
            Dim x As Integer
            Dim y As Integer
            y = r.Height - Osservazione.prezzo
            x = Osservazione.istante.Subtract(inizialeInstant).TotalSeconds
            Dim punto As New PointF(x, y)
            listSerieStorica.Add(punto)
        Next

        SerieAvg = New List(Of PointF)
        For Each Osservazione As Class1 In serieStorica
            Dim x As Integer
            Dim y As Integer
            y = r.Height - Osservazione.Avg
            x = Osservazione.istante.Subtract(inizialeInstant).TotalSeconds
            Dim punto1 As New PointF(x, y)
            SerieAvg.Add(punto1)
        Next

        SerieAvgMobile = New List(Of PointF)
        For Each Osservazione As Class1 In serieStorica
            Dim x As Integer
            Dim y As Integer
            y = r.Height - Osservazione.AvgMobile
            x = Osservazione.istante.Subtract(inizialeInstant).TotalSeconds
            Dim punto2 As New PointF(x, y)
            SerieAvgMobile.Add(punto2)
        Next

        SerieDeviazioneSup = New List(Of PointF)
        For Each Osservazione As Class1 In serieStorica
            Dim x As Integer
            Dim y As Integer
            y = r.Height - Osservazione.DeviazioneSup
            x = Osservazione.istante.Subtract(inizialeInstant).TotalSeconds
            Dim punto3 As New PointF(x, y)
            SerieDeviazioneSup.Add(punto3)
        Next

        SerieDeviazioneInf = New List(Of PointF)
        For Each Osservazione As Class1 In serieStorica
            Dim x As Integer
            Dim y As Integer
            y = r.Height - Osservazione.DeviazioneInf
            x = Osservazione.istante.Subtract(inizialeInstant).TotalSeconds
            Dim punto4 As New PointF(x, y)
            SerieDeviazioneInf.Add(punto4)
        Next


        Sell = New List(Of Double)
        Buy = New List(Of Double)
        SerieSell = New List(Of PointF)
        SerieBuy = New List(Of PointF)
        For Each Osservazione As Class1 In serieStorica
            Dim xs As Integer
            Dim ys As Integer
            Dim xb As Integer
            Dim yb As Integer
          
            If Osservazione.prezzo > Osservazione.DeviazioneSup Then
                ys = r.Height - Osservazione.DeviazioneSup
                xs = Osservazione.istante.Subtract(inizialeInstant).TotalSeconds
                Dim punto5 As New PointF(xs, ys)
                SerieSell.Add(punto5)
                Sell.Add(ys)
            ElseIf Osservazione.prezzo < Osservazione.DeviazioneInf Then
                yb = r.Height - Osservazione.DeviazioneInf
                xb = Osservazione.istante.Subtract(inizialeInstant).TotalSeconds
                Dim punto6 As New PointF(xb, yb)
                SerieBuy.Add(punto6)
                Buy.Add(yb)
            End If
        Next

        'Calcolo le coordinate reali della serie storica dei prezzi
        maxX = Double.MinValue
        minX = Double.MaxValue
        maxY = Double.MinValue
        minY = Double.MaxValue
        For Each punto As PointF In listSerieStorica
            If punto.X > maxX Then maxX = punto.X
            If punto.Y > maxY Then maxY = punto.Y
            If punto.X < minX Then minX = punto.X
            If punto.Y < minY Then minY = punto.Y
        Next

        B = New Bitmap(PictureBox1.Width, PictureBox1.Height)
        g = Graphics.FromImage(B)

        'Costruzione di una nuovi listi dei punti che vengono trasformati per rappresentare in Bitmap
        'e potere trascrivere all'interno del rectangolo

        PSs = New List(Of PointF)
        For Each punto As PointF In listSerieStorica
            xt = r.Left + (punto.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto.Y - minY) / (maxY - minY) * r.Height
            PSs.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        PAvg = New List(Of PointF)
        For Each punto1 As PointF In SerieAvg
            xt = r.Left + (punto1.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto1.Y - minY) / (maxY - minY) * r.Height
            PAvg.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        PAvgMobile = New List(Of PointF)
        For Each punto2 As PointF In SerieAvgMobile
            xt = r.Left + (punto2.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto2.Y - minY) / (maxY - minY) * r.Height
            PAvgMobile.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        PDeviazioneSup = New List(Of PointF)
        For Each punto3 As PointF In SerieDeviazioneSup
            xt = r.Left + (punto3.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto3.Y - minY) / (maxY - minY) * r.Height
            PDeviazioneSup.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        PDeviazioneInf = New List(Of PointF)
        For Each punto4 As PointF In SerieDeviazioneInf
            xt = r.Left + (punto4.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto4.Y - minY) / (maxY - minY) * r.Height
            PDeviazioneInf.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        PSell = New List(Of PointF)
        For Each punto5 As PointF In SerieSell
            xt = r.Left + (punto5.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto5.Y - minY) / (maxY - minY) * r.Height
            PSell.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        PBuy = New List(Of PointF)
        For Each punto6 As PointF In SerieBuy
            xt = r.Left + (punto6.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto6.Y - minY) / (maxY - minY) * r.Height
            PBuy.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        'Ciclo FOR per ottenere il beneficio. Questo ciclo ci dà tutte le transazioni con il proffito
        ' e proffito percentuale positiva
        Dim profit As Double = 0
        Dim Pprof As Double = 0
        For i As Integer = 0 To Buy.Count - 1
            For j As Integer = 0 To Sell.Count - 1
                profit = ((Sell(j)) - (Buy(i))) * Buy.Count
                Pprof = (profit / Buy(i)) * 100
                If profit > 0 Then
                    RichTextBox1.AppendText(vbCrLf & "Buy" & "       " & "Sell" & "       " & "Profit" & "           " & "%")
                    RichTextBox1.AppendText(vbCrLf & Buy(i).ToString("#.##").PadLeft(7) & Sell(j).ToString("#.##").PadLeft(7) & profit.ToString("#.##").PadLeft(8) & Pprof.ToString("#.##").PadLeft(13))
                End If
            Next
        Next


        g.Clear(Color.White)

        g.DrawLines(Pens.Black, PSs.ToArray)
        g.DrawLines(Pens.GreenYellow, PAvg.ToArray)
        g.DrawLines(Pens.Gold, PAvgMobile.ToArray)
        g.DrawLines(Pens.Blue, PDeviazioneSup.ToArray)
        g.DrawLines(Pens.Blue, PDeviazioneInf.ToArray)

        elipse()
        g.DrawRectangle(Pens.Black, r)
        PictureBox1.Image = B

        Dim drawFont2 As New Font("Arial", 12, FontStyle.Bold)
        g.DrawString("TRADING GRAPHIC", drawFont2, Brushes.Black, 300, 10)
    End Sub

    'Funzione MouseDown farvi sapere quale pulsante è stato premuto i la posizione all'interno del controllo
    Private Sub PictureBox1_MouseDown(ByVal sender As Object, ByVal e As System.Windows.Forms.MouseEventArgs) Handles PictureBox1.MouseDown
  

        'Contains() determina se un elemento è contenuto nella lista.
        If Not r.Contains(e.X, e.Y) Then Exit Sub
        If e.Button = Windows.Forms.MouseButtons.Left Then
            'la mano Cursor in genere indica che il puntatore si trova sopra un collegamento
            'modificare il cursore del mouse
            Cursor = Cursors.Hand
        ElseIf e.Button = Windows.Forms.MouseButtons.Right Then
            'Ottiene un nord-ovest a due picchi o verso sud-est il ridimensionamento Cursor
            'modificare il cursore del mouse
            Cursor = Cursors.SizeNWSE
        End If

        'Salvare posizione corrente del mouse e del rettangolo
        xiniziale = e.X
        yiniziale = e.Y
        rxiniziale = r.X
        ryiniziale = r.Y
        LarghezzaIniziale = r.Width
        AltezzaIniziale = r.Height

        'abilitare il flag
        draggingMove = True

    End Sub

    'La funzione MouseMove ci permette di modificare la posizione di rectangolo
    Private Sub PictureBox1_MouseMove(ByVal sender As Object, ByVal e As System.Windows.Forms.MouseEventArgs) Handles PictureBox1.MouseMove

   
        If Not draggingMove Then Exit Sub

        'Aggiorniamo le nuove coordinate del rettangolo
        dx = e.X - xiniziale
        dy = e.Y - yiniziale

        'condicione If per modificare le coordinate
        If e.Button = Windows.Forms.MouseButtons.Left Then
            'Se il pulsante sinistro del mouse è stato premuto applico al nuovo vertice del rettangolo
            r.X = rxiniziale + dx
            r.Y = ryiniziale + dy
        Else
            'Modifichiamo l'altezza e la larghezza
            r.Width = LarghezzaIniziale + dx
            r.Height = AltezzaIniziale + dy

        End If

        r = New Rectangle(r.X, r.Y, r.Width, r.Height)


        PSs = New List(Of PointF)
        For Each punto As PointF In listSerieStorica
            xt = r.Left + (punto.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto.Y - minY) / (maxY - minY) * r.Height
            PSs.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        PAvg = New List(Of PointF)
        For Each punto1 As PointF In SerieAvg
            xt = r.Left + (punto1.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto1.Y - minY) / (maxY - minY) * r.Height
            PAvg.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        PAvgMobile = New List(Of PointF)
        For Each punto2 As PointF In SerieAvgMobile
            xt = r.Left + (punto2.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto2.Y - minY) / (maxY - minY) * r.Height
            PAvgMobile.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        PDeviazioneSup = New List(Of PointF)
        For Each punto3 As PointF In SerieDeviazioneSup
            xt = r.Left + (punto3.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto3.Y - minY) / (maxY - minY) * r.Height
            PDeviazioneSup.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        PDeviazioneInf = New List(Of PointF)
        For Each punto4 As PointF In SerieDeviazioneInf
            xt = r.Left + (punto4.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto4.Y - minY) / (maxY - minY) * r.Height
            PDeviazioneInf.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        PSell = New List(Of PointF)
        For Each punto5 As PointF In SerieSell
            xt = r.Left + (punto5.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto5.Y - minY) / (maxY - minY) * r.Height
            PSell.Add(New PointF(CSng(xt), CSng(yt)))
        Next

        PBuy = New List(Of PointF)
        For Each punto6 As PointF In SerieBuy
            xt = r.Left + (punto6.X - minX) / (maxX - minX) * r.Width
            yt = r.Bottom - (punto6.Y - minY) / (maxY - minY) * r.Height
            PBuy.Add(New PointF(CSng(xt), CSng(yt)))
        Next




        g.Clear(Color.White)

        g.DrawLines(Pens.Black, PSs.ToArray)
        g.DrawLines(Pens.GreenYellow, PAvg.ToArray)
        g.DrawLines(Pens.Gold, PAvgMobile.ToArray)
        g.DrawLines(Pens.Blue, PDeviazioneSup.ToArray)
        g.DrawLines(Pens.Blue, PDeviazioneInf.ToArray)

        g.DrawRectangle(Pens.Black, r)
        PictureBox1.Image = B
        elipse()
        Dim drawFont2 As New Font("Arial", 12, FontStyle.Bold)
        g.DrawString("TRADING GRAPHIC", drawFont2, Brushes.Black, 300, 10)


    End Sub

    'Funzione MouseUp ci permette di trarre il rectangolo quando il pulsante del mouse viene rilasciato
    Private Sub PictureBox1_MouseUp(ByVal sender As Object, ByVal e As System.Windows.Forms.MouseEventArgs) Handles PictureBox1.MouseUp

        'flag per spostare il controllo
        draggingMove = False

        'modificare il cursore
        Cursor = Cursors.Default


    End Sub

    Private Sub elipse()
        For Each punto As PointF In PSell
            g.DrawEllipse(Pens.Red, punto.X, punto.Y, 9, 9)
        Next
        For Each punto As PointF In PBuy
            g.DrawEllipse(Pens.Green, punto.X, punto.Y, 9, 9)
        Next
    End Sub
    Private Sub NumericUpDown1_ValueChanged(ByVal sender As Object, ByVal e As System.EventArgs) Handles NumericUpDown1.ValueChanged


    End Sub

    Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load

    End Sub

End Class


Nessun commento:

Posta un commento