Eis uma linha de um ficheiro diário de ações. NVDA, sexta-feira, 7 de junho de 2024, a última sessão antes de o desdobramento de 10 para 1 entrar em vigor.
| Coluna | Valor |
|---|---|
| data | 2024-06-07 |
| fecho | 1208.88 |
| volume | 42,800,000 (arredondado) |
| fator_desdobramento | 1.0 |
| dividendo | 0.00 |
| fecho_ajustado | 120.8781 |
Deixei deliberadamente de fora desta vista as colunas OHLC. Voltam a aparecer perto do fim, e são elas que causam problemas sem dar nas vistas.
Tudo o que há de interessante nesta linha está na diferença entre a segunda e a sexta coluna. A 7 de junho, o mercado registou 1208.88. Nunca mais ninguém negociará a esse preço, no sentido em que a ação a que se referia já não existe como unidade. O valor 120.8781 é uma reconstrução, e não resulta simplesmente de dividir 1208.88 por dez. Vamos analisar coluna a coluna.
data: 2024-06-07, e as outras duas datas que mais importam
O desdobramento foi anunciado a 22 de maio de 2024, juntamente com os
resultados. A data de registo foi 6 de junho. A negociação numa base ajustada
ao desdobramento começou na segunda-feira, 10 de junho. São 3 datas, e a
coluna split_factor do seu fornecedor de dados corresponde
exatamente a uma delas, normalmente à primeira sessão já ajustada ao
desdobramento. Este erro de um dia é o problema mais comum que vejo nas ações
societárias e passa despercebido nos resultados agregados: a curva de capital
sofre uma queda de 90% ou uma subida de 900% num único dia. Um Sharpe
calculado ao longo de 2,000 dias mal acusa a diferença, mas o drawdown máximo
ou uma regra de stop-loss acusa-a sem dúvida.
O dividendo também tem um problema de datas, e as regras mudaram para todos em 2024. O dividendo trimestral de $0.01 da NVDA após o desdobramento tinha data de registo a 11 de junho. A liquidação nos EUA passou para T+1 a 28 de maio de 2024, o que significa que a data ex-dividendo e a data de registo são agora o mesmo dia. Qualquer carregador que calcule a data ex-dividendo como «data de registo menos um dia útil» — o que esteve correto durante décadas — começou, em junho de 2024, a aplicar silenciosamente os ajustes de dividendos uma sessão antes. Nada gera um erro. O fator simplesmente fica na linha errada.
O modo de falha do código de ações societárias nunca é uma exceção. É um número deslocado um dia, mas perfeitamente plausível.
fecho: 1208.88 — o preço que não está no ficheiro
Este é o registo bruto e, na maioria dos pipelines de investigação, existe
apenas como uma coluna que ninguém consulta. Os sinais são calculados sobre
adj_close. E qualquer regra que use um nível de preço por ação em
dólares passa a referir-se a um número que nenhum interveniente no mercado
alguma vez viu.
A subida gradual da NVDA até aos $1,000 na primavera de 2024 foi real e teve fluxo de ordens real por trás: números redondos a atrair o preço, strikes de opções concentrados nos 950 e 1000, risco associado às notícias em cada aproximação. Nos dados ajustados, todo esse episódio acontece a $100. Se está a testar o comportamento em torno de níveis psicológicos, a lógica de preenchimento de gaps perto de números redondos ou uma variável de proximidade a strikes, está a testar tudo isso sobre uma série de preços redimensionada por um evento que ainda não tinha acontecido.
O mesmo se aplica aos filtros do universo. «Excluir ações abaixo de $5» é um indicador válido de um conjunto real de problemas de microestrutura: spreads relativos amplos, regras de elegibilidade para margem, regimes de tick. Se aplicar esse filtro à história ajustada, exclui empresas durante períodos em que negociavam a $30 e que mais tarde fizeram um desdobramento inverso. Se aplicar «preço acima de $500», vai excluir silenciosamente a NVDA de todos os anos anteriores a junho de 2024. Os filtros de preço devem usar os preços não ajustados. Sem mais.
fator_desdobramento: 1.0 — e o 0.1 na linha seguinte
O fator é um produto acumulado calculado retroativamente a partir de hoje. Cada linha anterior a 10 de junho de 2024 inclui um fator de 0.1 deste desdobramento, multiplicado pelo 0.25 do desdobramento de 4 para 1 em 2021, multiplicado pelo que veio antes. O historial da NVDA anterior a 2021 é multiplicado por 0.025, pelo que uma barra com preço de $200 em 2019 aparece como $5.00.
Há duas consequências a reter. Primeiro, o historial ajustado muda sempre que ocorre uma nova ação societária. Um backtest executado em maio de 2024 e outro executado hoje produzem números diferentes com o mesmo código e as mesmas datas. E, se guardou variáveis em cache com chave de símbolo e data, mas sem uma versão dos dados, agora tem uma cache que mistura duas escalas. Incluímos a época do ajuste na chave das variáveis precisamente por este motivo; bastou-nos uma tarde bastante confusa para aprendermos a lição.
Segundo, com uma escala de 0.025, uma ação negociada em ticks de $0.01 passa a mover-se em incrementos de $0.00025. A lógica de arredondamento ao tick, as comparações do tipo «é um novo máximo» e as verificações de igualdade entre valores de vírgula flutuante: tudo passa a operar muito abaixo da resolução efetiva do mercado.
dividendo: 0.01 — o valor que retira todas as cotações da grelha de cêntimos
Um cêntimo. Parece ruído, mas é a razão pela qual
adj_close apresenta 120.8781 em vez de um valor exato de 120.888.
O fecho de 10 de junho foi 121.79. O fator ex-dividendo é (121.79 − 0.01) / 121.79 = 0.99991789. Esse fator multiplica todos os preços anteriores a 11 de junho, pelo que os 120.888 ajustados ao desdobramento passam a 120.878074. É uma alteração pequena, permanente e aplicada novamente em cada uma das mais de 60 datas ex-dividendo ao longo do historial da NVDA. O que conta é o efeito acumulado: quando recuamos até 2015, estamos a olhar para um preço multiplicado por dezenas de fatores pouco racionais. Nenhum preço histórico ajustado fica na grelha de cêntimos.
Isto significa que todas as comparações de == com um nível
redondo são falsas, todas as verificações do tipo «tocámos no preço limite?»
precisam de uma tolerância e os valores OHLC reconstruídos deixam de respeitar
a invariável low ≤ open ≤ high depois de um arredondamento ingénuo a 4 casas
decimais. Significa também que adj_close é uma série de retorno
total, enquanto close é uma série de retorno de preço. Se
calcular os retornos com uma e os drawdowns com a outra, está a misturar duas
definições diferentes do que aconteceu.
volume: 42,800,000 — o divisor que ninguém aplica de forma consistente
Para comparar o volume de ações com o das sessões após o desdobramento, é preciso multiplicá-lo por 10. Alguns fornecedores fazem-no. Outros não. Há ainda os que ajustam o OHLC e deixam o volume bruto, o pior dos três casos, porque o ficheiro parece coerente até multiplicarmos o preço pelo volume.
A opção sensata é deixar de usar o volume de ações como variável e usar o volume em dólares, que é invariável aos desdobramentos por definição. Um filtro de liquidez baseado no volume médio em dólares a 20 dias não precisa de qualquer lógica de ajuste e não pode ser afetado por uma ação societária. A invariância das variáveis é melhor do que ter código de ajuste correto, porque é preciso continuar a acertar no código de ajuste.
3 formatos de ficheiro de fornecedores, 3 modos de falha.
| O que é fornecido | O que falha |
|---|---|
| Apenas fecho ajustado, OHLC bruto | A lógica de gaps e intradiária calcula com duas escalas de preços |
| OHLC ajustado, volume bruto | Volume em dólares desfasado pelo rácio do desdobramento; os filtros ADV falham |
| OHLCV bruto e colunas de fatores | Nada, se aplicar os fatores. Tudo, se os aplicar na linha errada |
As colunas que faltam: adj_open, adj_high, adj_low
Agora voltemos a incluir o OHLC. Se um feed ajustar apenas o fecho e a sua
estratégia calcular um gap overnight como
open / prev_adj_close − 1, a 10 de junho de 2024 calcula 120.37 /
120.8781 − 1, um valor perfeitamente razoável, cerca de −0.4%. Aplique o mesmo
código a 7 de junho de 2024 e calcula a abertura a partir do ficheiro bruto
(cerca de 1207) contra um fecho ajustado por 0.025 devido a desdobramentos
anteriores, produzindo um gap de vários milhares por cento.
Qualquer operação que misture uma coluna bruta com uma ajustada faz contas entre dois sistemas de coordenadas. Agora trato as leituras com ajustes mistos como uma asserção ao nível do carregador, em vez de deixar ao investigador a responsabilidade de se lembrar, porque ninguém se vai lembrar, nem eu.
O que nenhuma coluna lhe diz: quantas ações teria realmente comprado
Este problema afeta o modelo de custos do backtest e é a razão pela qual estou a escrever sobre um desdobramento de ações.
As comissões sobre ações nos EUA são frequentemente cobradas por ação. Consideremos $0.005, com uma comissão mínima de $1.00 por ordem, um escalão fixo comum nos corretores de retalho. Agora faça o backtest de uma posição de $400,000 em NVDA um ano antes do desdobramento, quando o preço bruto rondava os $400 e o preço ajustado aparece como $40.
| Ações | Comissão | |
|---|---|---|
| O que aconteceu (preço bruto de $400) | 1,000 | $5.00 |
| O que o backtest vê (preço ajustado de $40) | 10,000 | $50.00 |
A mesma exposição, a mesma operação, 10x o custo modelado. São $45 fictícios por operação, $90 por operação de ida e volta, e uma estratégia com rotação diária acumula cerca de $22,000 anuais em custos que nunca existiram. Num capital de $400k, 5.6 pontos percentuais de retorno anual, inventados por um divisor. Neste caso, faz com que o resultado pareça pior do que a realidade, o que é suportável.
Os desdobramentos inversos produzem o efeito contrário, e é aí que mora o perigo. Um desdobramento inverso de 1 para 10 faz com que o historial ajustado apresente preços 10x superiores e contagens de ações 10x inferiores às que teria negociado. O seu modelo de custos divide silenciosamente por 10 a comissão por ação. Os desdobramentos inversos são comuns no universo de empresas de pequena capitalização, abaixo de $5 e com spreads amplos, onde as comissões por ação são a maior rubrica individual da estrutura de custos. O backtest favorece precisamente os títulos que devia penalizar.
A solução é simples e estrutural: dimensione as posições em dólares, converta esse valor em ações usando o preço não ajustado dessa data e cobre as comissões por ação sobre essa quantidade. Mantenha a coluna de preços brutos no carregador para sempre, não como registo de auditoria, mas como dado ativo para o motor de execução.
- Sinais e retornos: séries ajustadas.
- Contagens de ações, comissões por ação, arredondamento ao tick e filtros por nível de preço: séries não ajustadas.
- Liquidez e capacidade: volume em dólares, que dispensa ambos.
6 colunas, 1 linha, uma ação societária bastante comum, anunciada com 3 semanas de antecedência e que não surpreendeu ninguém. O mercado tratou do assunto numa manhã. Reproduzi-la fielmente num pipeline de investigação é bem mais difícil, e o sinal de que um pipeline não o conseguiu quase nunca é uma mensagem de erro.
← Todos os artigos


