Aprendizado de máquina no trading: teoria, prática, negociação e não só - página 21

 
Dr. Trader:

Eu tentei Y-scale também, R^2 em ambos os casos (com e sem Y-scale) saiu o mesmo (mesmo que eles usem pacotes diferentes!).

Acho que a escala Y pode dar o mesmo bom resultado com menos componentes principais. Mas, se mesmo usando todos os componentes o resultado ainda não é satisfatório (como no meu caso) - não há diferença. Além disso, funciona mais rápido, o que é mais importante para mim agora. Mas não provei pela teoria ou pela prática se este método é adequado para a seleção de preditores... No início tive a idéia de modelar os componentes principais em todos os preditores e selecionar os preditores através da análise dos coeficientes dos componentes. Mas depois reparei que com a adição de lixo - R^2 do modelo cai. Faz sentido tentar diferentes conjuntos de preditores e procurar por aqueles com R^2 mais alto, mas é apenas uma teoria.

Eu faço aqui regularmente a seguinte sugestão: se você destilar o seu conjunto para mim, vamos comparar os meus resultados com os seus.

Para mim, o ideal é .RData. Um quadro em que o alvo é binário e os preditores são de preferência números reais.

 
Dr. Trader:

Eu costumava treinar a floresta e devolver um erro em uma amostra de validação. Em princípio, funcionou - se a floresta se sobrepõe aos comboios, mesmo que um pouco, o erro tende a 50%.

Agora eu uso GetPCrsquared(), esse código acima. Também tenho o seu exemplo do feature_selector_modeller.txt mas tenho de o descobrir e obter o fragmento de código necessário, por isso ainda não verifiquei os meus dados.

Aqui está o que precisas de levar lá:

library(infotheo) # measured in nats, converted to bits

library(scales)

library(GenSA)


#get data

sampleA <- read.table('C:/Users/aburnakov/Documents/Private/dummy_set_features.csv'

, sep= ','

, header = T)




#calculate parameters

predictor_number <- dim(sampleA)[2] - 1

sample_size <- dim(sampleA)[1]

par_v <- runif(predictor_number, min = 0, max = 1)

par_low <- rep(0, times = predictor_number)

par_upp <- rep(1, times = predictor_number)



#load functions to memory

shuffle_f_inp <- function(x = data.frame(), iterations_inp, quantile_val_inp){

mutins <- c(1:iterations_inp)

for (count in 1:iterations_inp){

xx <- data.frame(1:dim(x)[1])

for (count1 in 1:(dim(x)[2] - 1)){

y <- as.data.frame(x[, count1])

y$count <- sample(1 : dim(x)[1], dim(x)[1], replace = F)

y <- y[order(y$count), ]

xx <- cbind(xx, y[, 1])

}

mutins[count] <- multiinformation(xx[, 2:dim(xx)[2]])

}

quantile(mutins, probs = quantile_val_inp)

}



shuffle_f <- function(x = data.frame(), iterations, quantile_val){

height <- dim(x)[1]

mutins <- c(1:iterations)

for (count in 1:iterations){

x$count <- sample(1 : height, height, replace = F)

y <- as.data.frame(c(x[dim(x)[2] - 1], x[dim(x)[2]]))

y <- y[order(y$count), ]

x[dim(x)[2]] <- NULL

x[dim(x)[2]] <- NULL

x$dep <- y[, 1]

rm(y)

receiver_entropy <- entropy(x[, dim(x)[2]])

received_inf <- mutinformation(x[, 1 : dim(x)[2] - 1], x[, dim(x)[2]])

corr_ff <- received_inf / receiver_entropy

mutins[count] <- corr_ff

}

quantile(mutins, probs = quantile_val)

}


############### the fitness function

fitness_f <- function(par){

indexes <- c(1:predictor_number)

for (i in 1:predictor_number){

if (par[i] >= threshold) {

indexes[i] <- i

} else {

indexes[i] <- 0

}

}

local_predictor_number <- 0

for (i in 1:predictor_number){

if (indexes[i] > 0) {

local_predictor_number <- local_predictor_number + 1

}

}

if (local_predictor_number > 1) {

sampleAf <- as.data.frame(sampleA[, c(indexes[], dim(sampleA)[2])])

pred_entrs <- c(1:local_predictor_number)

for (count in 1:local_predictor_number){

pred_entrs[count] <- entropy(sampleAf[count])

}

max_pred_ent <- sum(pred_entrs) - max(pred_entrs)

pred_multiinf <- multiinformation(sampleAf[, 1:dim(sampleAf)[2] - 1])

pred_multiinf <- pred_multiinf - shuffle_f_inp(sampleAf, iterations_inp, quantile_val_inp)

if (pred_multiinf < 0){

pred_multiinf <- 0

}

pred_mult_perc <- pred_multiinf / max_pred_ent

inf_corr_val <- shuffle_f(sampleAf, iterations, quantile_val)

receiver_entropy <- entropy(sampleAf[, dim(sampleAf)[2]])

received_inf <- mutinformation(sampleAf[, 1:local_predictor_number], sampleAf[, dim(sampleAf)[2]])

if (inf_corr_val - (received_inf / receiver_entropy) < 0){

fact_ff <- (inf_corr_val - (received_inf / receiver_entropy)) * (1 - pred_mult_perc)

} else {

fact_ff <- inf_corr_val - (received_inf / receiver_entropy)

}

} else if (local_predictor_number == 1) {

sampleAf<- as.data.frame(sampleA[, c(indexes[], dim(sampleA)[2])])

inf_corr_val <- shuffle_f(sampleAf, iterations, quantile_val)

receiver_entropy <- entropy(sampleAf[, dim(sampleAf)[2]])

received_inf <- mutinformation(sampleAf[, 1:local_predictor_number], sampleAf[, dim(sampleAf)[2]])

fact_ff <- inf_corr_val - (received_inf / receiver_entropy)

} else  {

fact_ff <- 0

}

return(fact_ff)

}



########## estimating threshold for variable inclusion


iterations = 5

quantile_val = 1


iterations_inp = 1

quantile_val_inp = 1


levels_arr <- numeric()

for (i in 1:predictor_number){

levels_arr[i] <- length(unique(sampleA[, i]))

}


mean_levels <- mean(levels_arr)

optim_var_num <- log(x = sample_size / 100, base = round(mean_levels, 0))


if (optim_var_num / predictor_number < 1){

threshold <- 1 - optim_var_num / predictor_number

} else {

threshold <- 0.5

}



#run feature selection


start <- Sys.time()


sao <- GenSA(par = par_v, fn = fitness_f, lower = par_low, upper = par_upp

     , control = list(

      #maxit = 10

        max.time = 1200

        , smooth = F

        , simple.function = F))


trace_ff <- data.frame(sao$trace)$function.value

plot(trace_ff, type = "l")

percent(- sao$value)

final_vector <- c((sao$par >= threshold), T)

names(sampleA)[final_vector]

final_sample <- as.data.frame(sampleA[, final_vector])


Sys.time() - start

No campo de dados, a coluna mais à direita é a coluna de destino.

TODAS as colunas devem ser categorias (ineteger, personagem ou fator).

E você tem que carregar todas as bíblias.

Um pedaço de código que mostra como traduzir números em variáveis categóricas:

disc_levels <- 3 # сколько равночастотных уровней переменной создается


for (i in 1:56){

naming <- paste(names(dat[i]), 'var', sep = "_")

dat[, eval(naming)] <- discretize(dat[, eval(names(dat[i]))], disc = "equalfreq", nbins = disc_levels)[,1]

}

 

Achei esta função interessante na internet.

data_driven_time_warp <- function (y) {
  cbind(
    x = cumsum(c(0, abs(diff(y)))),
    y = y
  )
}


y <- cumsum(rnorm(200))+1000
i <- seq(1,length(y),by=10)
op <- par(mfrow=c(2,1), mar=c(.1,.1,.1,.1))
plot(y, type="l", axes = FALSE)
abline(v=i, col="grey")
lines(y, lwd=3)
box()
d <- data_driven_time_warp(y)
plot(d, type="l", axes=FALSE)
abline(v=d[i,1], col="grey")
lines(d, lwd=3)
box()
par(op)

Talvez nesta forma o algoritmo reconheça melhor os dados? Mas há um problema, a saída da função é uma variável "d" e tem uma matriz com duas colunas "x" e "y", uma denota o preço e a segunda o tempo curvado pelo algoritmo, a questão é como transformar esta matriz em um vetor para que ela não perca suas propriedades

 
SanSanych Fomenko:

Eu faço aqui regularmente a seguinte sugestão: se você distribuir o seu conjunto para mim, vamos comparar os meus resultados com os seus.

Para mim, o ideal é um .RData. Um quadro em que o alvo binário e os preditores são de preferência números reais.

Ataque é o meu melhor conjunto de preditores. TrainData é D1 para eurusd para 2015, fronttestData é de 1 de janeiro de 2016 a junho. Fronttest é um pouco longo, na negociação real é improvável que eu negocie por mais de um mês com as mesmas configurações, só queria ver quanto tempo a rentabilidade do modelo realmente dura. FronttestData1, fronttestData2, fronttestData3 são cortes separados de fronttestData, apenas para Janeiro, apenas para Fevereiro, apenas para Março. Eu só estou realmente interessado em baixar o erro no fronttestData1, o resto é só para pesquisa. O conjunto de preditores contém principalmente indicadores e diferentes cálculos entre eles. Com nnet erro no fronttest eu tenho 30% no fronttestData1, treinamento com controle de iteração e número de encaixe de neurônios internos. Eu acho que os 30% aqui é apenas uma questão de sorte, o modelo pegou alguma tendência no mercado de março de 2015 a fevereiro de 2016. Mas o facto de os outros períodos também não se fundirem já é bom.

Aqui está uma foto do testador mt5 2014.01-2016.06, eu marquei o período de treinamento com uma moldura. Já é melhor do que era :). Por agora este é o meu limite, tenho de resolver muitos problemas com indicadores, nomeadamente as suas configurações padrão estão estritamente ligadas a prazos, por exemplo no H1 a minha experiência é completamente inútil, o mesmo algoritmo de selecção de indicadores no H1 considera tudo lixo. Eu deveria ou adicionar um monte de suas variações com parâmetros diferentes ao conjunto inicial de indicadores ou gerar indicadores aleatórios do ohlc por mim mesmo.

Arquivos anexados:
 
Alexey Burnakov:

há isto para levar:

Isso faz mais sentido, obrigado. Parece-me que apenas 3 categorias por indicador não servem. Logicamente, eu faria pelo menos 100 níveis, mas é melhor ou perde o sentido do algoritmo?

 
Dr. Trader:

Isso faz mais sentido, obrigado. Parece-me que apenas 3 categorias por indicador não servem. Logicamente, eu faria pelo menos 100 níveis, mas é melhor ou faz o algoritmo perder o seu significado?

O algoritmo vai perder o seu significado. O algoritmo conta o número total de níveis de variáveis de entrada e distribuídas por esses níveis de níveis de resposta. Assim, se o número de valores de resposta em cada um dos níveis de input for muito baixo, será impossível avaliar a significância estatística do enviesamento de probabilidade.

Se você fizer 100 níveis, sim, haverá muitas variáveis. Então o algoritmo retornará significado zero para qualquer subconjunto, o que é razoável dado o tamanho limitado da amostra.

O exemplo é bom.

níveis de entrada | número de observações

1 150

2 120

...

9 90

aqui podemos estimar o significado dentro de uma resposta

exemplo - mau.

níveis de entrada

112 5

...

357 2

...

1045 1

o significado dentro de uma resposta não pode ser estimado aqui

 
Dr. Trader:

Ataque é o meu melhor conjunto de preditores. TrainData é D1 para eurusd para 2015, fronttestData é de 1 de janeiro de 2016 a junho. Fronttest é um pouco longo, na negociação real é improvável que eu negocie por mais de um mês com as mesmas configurações, eu só queria ver quanto tempo a rentabilidade do modelo realmente dura. FronttestData1, fronttestData2, fronttestData3 são cortes separados de fronttestData, apenas para Janeiro, apenas para Fevereiro, apenas para Março. Eu só estou realmente interessado em baixar o erro no fronttestData1, o resto é só para pesquisa. O conjunto de preditores contém principalmente indicadores e diferentes cálculos entre eles. Com erro nnet no fronttest eu tenho 30% no fronttestData1, treinamento com controle de iteração e número de encaixe de neurônios internos. Eu acho que os 30% aqui é apenas uma questão de sorte, o modelo pegou alguma tendência no mercado de março de 2015 a fevereiro de 2016. Mas o facto de o resto dos períodos não se fundirem já é bom.

Aqui está uma foto do testador mt5 2014.01-2016.06, eu marquei o período de treinamento com uma moldura. Já é melhor do que era :). Por agora este é o meu limite, tenho de resolver muitos problemas com indicadores, nomeadamente as suas configurações padrão estão estritamente ligadas a prazos, por exemplo no H1 a minha experiência é completamente inútil, o mesmo algoritmo de selecção de indicadores no H1 considera tudo lixo. Eu preciso ou adicionar ao conjunto original de indicadores um monte de variações com parâmetros diferentes, ou de alguma forma gerar indicadores aleatórios do ohlc.

Nada mal, mas os períodos em si fora da amostra são pequenos.

Também não está claro quantos negócios caem fora da amostra. Há dúzias, centenas, qual é a ordem?

 
Dr. Trader:

Ataque é o meu melhor conjunto de preditores. TrainData é D1 para eurusd para 2015, fronttestData é de 1 de janeiro de 2016 a junho. Fronttest é um pouco longo, na negociação real é improvável que eu negocie por mais de um mês com as mesmas configurações, eu só queria ver quanto tempo a rentabilidade do modelo realmente dura. FronttestData1, fronttestData2, fronttestData3 são cortes separados de fronttestData, apenas para Janeiro, apenas para Fevereiro, apenas para Março. Eu só estou realmente interessado em baixar o erro no fronttestData1, o resto é só para pesquisa. O conjunto de preditores contém principalmente indicadores e diferentes cálculos entre eles. Com nnet erro no fronttest eu tenho 30% no fronttestData1, treinamento com controle de iteração e número de encaixe de neurônios internos. Eu acho que os 30% aqui é apenas uma questão de sorte, o modelo pegou alguma tendência no mercado de março de 2015 a fevereiro de 2016. Mas o facto de os outros períodos também não se fundirem já é bom.

Aqui está uma foto do testador mt5 2014.01-2016.06, eu marquei o período de treinamento com uma moldura. Já é melhor do que era :). Por agora este é o meu limite, tenho de resolver muitos problemas com indicadores, nomeadamente as suas configurações padrão estão estritamente ligadas a prazos, por exemplo no H1 a minha experiência é completamente inútil, o mesmo algoritmo de selecção de indicadores no H1 considera tudo lixo. Eu preciso ou adicionar ao conjunto original de indicadores um monte de variações com parâmetros diferentes, ou de alguma forma gerar indicadores aleatórios do ohlc.

Eu olhei para ele.

Compreendi correctamente que existem 107 linhas (107 observações) no conjunto total de dados?

 
SanSanych Fomenko:

Vejam só.

Entendi corretamente que o conjunto de dados total tem 107 filas (107 observações)?

Não, o conjunto de formação tem 250-linhas (número de dias de negociação em 2015). Eu treinei o modelo na tabela de dados do trem. Testei-o no fronttestData1. Tudo o resto é para verificações adicionais, você pode ignorá-las.

trainData - o ano inteiro de 2015.
fronttestData1 - Janeiro 2016
fronttestData2 - fevereiro 2016
fronttestData3 - Março 2016
fronttestData - Janeiro 2016 - Junho 2016

 
Dr. Trader:

Não, o conjunto de formação tem 250-linhas (número de dias de negociação em 2015). Eu treinei o modelo na tabela de dados do trem. Testei-o no fronttestData1. Tudo o resto é para cheques extra, podes ignorá-los.

trainData - o ano inteiro de 2015.
fronttestData1 - Janeiro 2016
fronttestData2 - fevereiro 2016
fronttestData3 - Março 2016
fronttestData - Janeiro 2016 - Junho 2016

Para mim isto é muito pouco - eu uso estatísticas. Mesmo para a janela actual 107 filas é muito pequena para mim. Eu uso mais de 400 para a janela actual.

Geralmente em seus conjuntos o número de observações é comparável ao número de preditores. Estes são conjuntos muito específicos. De alguma forma eu vi que tais conjuntos requerem métodos especiais. Não tenho referências, pois não tenho tais problemas.

Infelizmente os meus métodos não são adequados para os seus dados.