Módulo 08 AdmTech · Computação · Semana 6 · 18/11/2026
| Bloco | Minutos | Tema | Interação que fecha o bloco |
|---|---|---|---|
| Daily | 15 | O que fiz, o que vou fazer, impedimentos | tempo do motor do grupo para 10.000 carteiras |
| 1 | 0 a 15 | Da covariância às carteiras sorteadas | Peer Instruction sobre a melhor sorteada |
| 2 | 15 a 30 | Pesos, retorno e risco em forma vetorial | previsão antes do triângulo de pesos |
| 3 | 30 a 45 | O motor vetorizado de Monte Carlo | dupla no notebook, seções 1 a 3 |
| 4 | 45 a 60 | A melhor sorteada contra a ótima | quantos sorteios faltariam |
| 5 | 60 a 75 | Otimização com restrições e SLSQP | previsão da carteira mais concentrada |
| 6 | 75 a 90 | As duas ótimas e a fronteira de 50 pontos | dupla no notebook, seções 4 e 5 |
| 7 | 90 a 105 | Quiz e amarração com a Sprint 3 | quiz de três perguntas |
Horários de relógio a confirmar na Adalove; os blocos contam do fim da daily.
Módulo 08 AdmTech · Aula 04 · Sprint 3
2
A matriz de covariância da Aula 03 entra inteira, na mesma janela: 15 retornos esperados mais 120 variâncias e covariâncias distintas.
Regra da ADR-009: a lacuna de 24/10/2025 é preenchida com o último preço, como no ADR da Aula 01, e a cesta usa a janela comum dos 15 ativos, 1.423 retornos de 14/12/2020 a 31/08/2026.
Com a matriz pronta, como o grupo escolhe os pesos dos 15 ativos?
| Trio de hoje | Volatilidade, série inteira | Volatilidade, janela comum | Correlação com PETR4 |
|---|---|---|---|
| PETR4 | 39,25% | 33,40% | 1 |
| IVVB11 | 20,15% | 17,66% | -0,09 |
| GOLD11 | 19,80% | 19,80% | -0,13 |
Custo da janela comum: com a GOLD11, cotada desde 11/12/2020, a cesta perde março de 2020, e a volatilidade da PETR4 cai de 39,25% (série inteira, Aula 02) para 33,40%.
Módulo 08 AdmTech · Aula 04 · Sprint 3 · [1]
3
Entre 10.000 carteiras sorteadas com os 15 ativos, a de maior Índice de Sharpe é a carteira ótima?
Módulo 08 AdmTech · Aula 04 · Sprint 3
4
| Carteira | Sharpe | Retorno | Volatilidade | Ativos com peso | Maior peso |
|---|---|---|---|---|---|
| Melhor de 10.000 sorteadas | 0,41 | 16,62% | 13,05% | 15 | 18,17% |
| Máximo Sharpe, SLSQP | 0,92 | 25,96% | 15,91% | 3 | 44,31% em PETR4 |
Sorteio com semente 42 e pesos Uniform(0,1) divididos pela soma, uma distribuição que acumula as carteiras perto de 1/15 por ativo (slide 14). A carteira ótima concentra o peso em 3 dos 15 ativos e zera os outros 12.
Módulo 08 AdmTech · Aula 04 · Sprint 3 · [1] [6]
5
# mu: retorno esperado anual (15)
# cov: covariância anual (15 x 15)
# rf: CDI anualizado na janela
def metricas(w, mu, cov, rf):
retorno = w @ mu
volatilidade = np.sqrt(w @ cov @ w)
sharpe = (retorno - rf) / volatilidade
return retorno, volatilidade, sharpe
w = np.full(15, 1 / 15)
metricas(w, mu, cov, rf)
| Retorno | w · μ, a média dos retornos ponderada pelos pesos |
| Variância | wT Σ w, que soma cada covariância ponderada pelo par de pesos |
| Sharpe | (retorno - CDI) / volatilidade: prêmio sobre o CDI por unidade de risco |
| Pesos iguais | retorno 8,34% contra CDI de 11,30%, volatilidade 16,31%, Sharpe -0,18 |
Oito dos 15 ativos rendem abaixo do CDI na janela, e a MGLU3 tem retorno esperado de -42,83% ao ano.
Módulo 08 AdmTech · Aula 04 · Sprint 3 · [2] [5] [8]
7
Antes de arrastar: anotem onde o ponto cai no plano com 100% em PETR4 e onde fica o maior Sharpe.
Módulo 08 AdmTech · Aula 04 · Sprint 3
8
def sortear(n, mu, cov, rf, semente=42):
gerador = np.random.default_rng(semente)
pesos = gerador.random((n, len(mu)))
pesos /= pesos.sum(axis=1, keepdims=True)
retorno = pesos @ mu
volatilidade = np.sqrt(np.einsum(
"ij,jk,ik->i", pesos, cov, pesos))
sharpe = (retorno - rf) / volatilidade
return pesos, retorno, volatilidade, sharpe
pesos, ret, vol, sharpe = sortear(
10_000, mu, cov, rf)
| Semente | o mesmo sorteio em qualquer máquina, para o teste do SPEC.md |
| Normalizar | cada linha dividida pela própria soma: pesos somam 1, nenhum negativo, e a distribuição se acumula perto de 1/15 |
| einsum | wT Σ w das 10.000 linhas de uma vez, sem laço em Python |
| Requisito | o A3 pede 10.000 carteiras em menos de 10 segundos |
Módulo 08 AdmTech · Aula 04 · Sprint 3 · [2] [7]
9
sortear a linha que faz os pesos somarem 1 e a que calcula a variância sem laço.for w in pesos: w @ cov @ w e confiram com np.allclose que ele bate com o einsum.Checagem aos 6 min: o tempo das 10.000 carteiras e a contagem abaixo do CDI estão anotados. Debrief: ao fim do cronômetro, a turma compara os tempos medidos e a contagem abaixo do CDI entre as duplas.
Abrir o notebook da Aula 04 no Colab
Módulo 08 AdmTech · Aula 04 · Sprint 3
10
Antes de tocar: anotem onde a melhor sorteada vai parar, no meio da nuvem ou na borda de cima.
Módulo 08 AdmTech · Aula 04 · Sprint 3
11
Quantos sorteios faltariam para a melhor sorteada encostar na ótima?
Módulo 08 AdmTech · Aula 04 · Sprint 3
12
| Sorteios | Melhor Sharpe |
|---|---|
| 10 | -0,10 |
| 100 | 0,15 |
| 1.000 | 0,28 |
| 10.000 | 0,41 |
| 100.000 | 0,41 |
| 1.000.000 | 0,60 |
| SLSQP | 0,92 |
O motor soma 15 números Uniform(0,1) e divide cada um pela soma. Essa distribuição acumula os pesos perto de 1/15: o maior peso entre as 10.000 sorteadas é 24,61%.
A ótima põe 44,31% na PETR4 e zera 12 ativos, uma região que essa distribuição quase nunca visita. O slide seguinte troca a distribuição e mantém os 10.000 sorteios.
Quantos sorteios faltariam para a melhor sorteada encostar na ótima?
Módulo 08 AdmTech · Aula 04 · Sprint 3
13
| 10.000 sorteios, semente 42 | Melhor Sharpe | Maior peso da melhor | Ativos efetivos, mediana | Carteiras com peso acima de 25% |
|---|---|---|---|---|
| Uniform(0,1) dividido pela soma, o motor da aula | 0,41 | 18,17% | 11,41 | 0,00% |
| Dirichlet(1), uniforme no simplex | 0,64 | 55,26% | 8,37 | 26,21% |
| Dirichlet(0,2), mais peso nos vértices | 0,85 | 68,35% | 3,70 | 94,91% |
| Máximo Sharpe, SLSQP | 0,92 | 44,31% | 2,82 na ótima | não se aplica |
| Distribuição | com o mesmo orçamento, a Dirichlet(1) chega a 0,64 e passa do milhão de sorteios do motor da aula (0,60) |
| Dimensão | no trio PETR4, IVVB11 e GOLD11, as três distribuições chegam a 0,92 com 10.000 sorteios; com 15 ativos, nenhuma chega |
| Objetivo | o sorteio não usa o Sharpe para decidir onde sortear; o SLSQP usa, e por isso o A4 resolve a carteira por otimização |
Ativos efetivos = 1 / soma dos pesos ao quadrado: 15 com pesos iguais, 1 com todo o peso num ativo.
Módulo 08 AdmTech · Aula 04 · Sprint 3 · [7] [9]
14
from scipy.optimize import minimize
n = len(mu)
soma_1 = {"type": "eq",
"fun": lambda w: w.sum() - 1}
limites = [(0, 1)] * n # sem venda a descoberto
inicio = np.full(n, 1 / n)
def menos_sharpe(w):
return -(w @ mu - rf) / np.sqrt(w @ cov @ w)
ms = minimize(menos_sharpe, inicio, method="SLSQP",
bounds=limites, constraints=[soma_1])
mv = minimize(lambda w: w @ cov @ w, inicio,
method="SLSQP", bounds=limites,
constraints=[soma_1])
| Objetivo | o que se minimiza: a variância, ou o Sharpe com sinal trocado |
| Restrição | igualdade: os pesos somam 1 |
| Limites | cada peso entre 0 e 1, sem venda a descoberto |
| Conferir | ms.success antes de usar ms.x |
Módulo 08 AdmTech · Aula 04 · Sprint 3 · [3] [6]
16
Antes de rodar: qual das duas, variância mínima ou máximo Sharpe, vai concentrar mais peso num único ativo? A previsão fica no quadro.
Módulo 08 AdmTech · Aula 04 · Sprint 3 · [6]
17
| Medida | Variância mínima | Máximo Sharpe |
|---|---|---|
| Retorno | 14,10% | 25,96% |
| Volatilidade | 9,67% | 15,91% |
| Sharpe | 0,29 | 0,92 |
| Ativos com peso | 10 | 3 |
| Maior peso | 26,78% IVVB11 | 44,31% PETR4 |
| Ativo | Variância mínima | Máximo Sharpe |
|---|---|---|
| PETR4 | 5,06% | 44,31% |
| IVVB11 | 26,78% | 23,97% |
| GOLD11 | 24,71% | 31,72% |
| EGIE3 | 17,20% | 0% |
| outros 6 | 26,27% | 0% |
Confiram a previsão do quadro. A variância mínima espalha o peso em 10 ativos e fica com a menor volatilidade possível da cesta.
Módulo 08 AdmTech · Aula 04 · Sprint 3
18
Cada um dos 50 pontos é a carteira de menor volatilidade para um retorno alvo, de 14,10% (variância mínima) a 37,53% (só PETR4).
Módulo 08 AdmTech · Aula 04 · Sprint 3 · [3] [4]
19
success.maximo_sharpe_com_teto e comparem os pesos com os da seção 4.Checagem aos 6 min: a tabela das duas ótimas está na tela, com os ativos de peso zero apontados. Debrief: ao fim do cronômetro, duas duplas leem a frase do perfil, e a sala confere se alguma sorteada passa da fronteira.
Módulo 08 AdmTech · Aula 04 · Sprint 3
20
1. Por que o sorteio não encontra a carteira de máximo Sharpe?
2. O que impede venda a descoberto no SLSQP?
3. Qual ótima tem a menor volatilidade?
Módulo 08 AdmTech · Aula 04 · Sprint 3
21
| Seção | O que entrega |
|---|---|
| 1 e 2 | Retornos, mu, cov, o CDI e as métricas em forma vetorial |
| 3 | O motor vetorizado, o tempo medido e a nuvem colorida por Sharpe |
| 4 | Variância mínima e máximo Sharpe com SLSQP, e a tabela comparativa |
| 5 | A fronteira de 50 pontos sobre a nuvem |
| 6 | Desafio: peso máximo por ativo e a comparação com os pesos da aula |
Notebook no GitHub · Abrir no Colab
Módulo 08 AdmTech · Aula 04 · Sprint 3
22
| Critério do A3 | Peso | O que hoje já adiantou |
|---|---|---|
| Corretude da simulação | 30% | pesos normalizados e as três métricas por carteira |
| Desempenho | 10% | motor vetorizado, bem abaixo dos 10 segundos |
| Qualidade do gráfico | 10% | nuvem colorida por Sharpe, com o CDI marcado |
| Leitura analítica | 15% | por que a simulação não substitui a otimização: 0,41 contra 0,92 |
| Especificação e documentação | 15% | SPEC.md com teste de semente fixa e pesos somando 1 |
| ADRs, nota individual | 20% | número de simulações e vetorização, com o tempo medido |
A3 vale 3 pontos: review da Sprint 3 em 19/11/2026 e entrega na sexta, 20/11/2026, 23h59. O A4 (3 pontos) leva o otimizador de hoje para um módulo Python; a Adalove o lista nas Sprints 3 e 4.
Módulo 08 AdmTech · Aula 04 · Sprint 3
23
Módulo 08 AdmTech · Aula 04 · Sprint 3
24