⚙️ Motore del Portafoglio — Modello Matematico
💡 Panoramica
Questa pagina definisce formalmente il modello matematico alla base del motore di calcolo del portafoglio di LibreFolio. Tutte le altre pagine delle metriche (NAV, Valore contabile, P&L periodo, Rendimento sul costo, PMC, Capitale Versato) fanno riferimento a questa pagina per le loro precise regole di calcolo.
📐 1. Notazione e Insiemi
| Simbolo | Significato |
|---|---|
| \(V(u)\) | Tutti i broker visibili all'utente \(u\) |
| \(S \subseteq V(u)\) | Ambito dei broker selezionati (filtrati) |
| \(A\) | Insieme degli asset con posizioni |
| \(C^*\) | Valuta obiettivo |
| \([t_0, t_1]\) | Intervallo di valutazione richiesto |
| \(q(a,b,t)\) | Quantità dell'asset \(a\) presso il broker \(b\) alla data \(t\) |
| \(p(a,t)\) | Prezzo di valutazione dell'asset \(a\) alla data \(t\) |
| \(\mathrm{fx}(c_1, c_2, t)\) | Tasso di cambio dalla valuta \(c_1\) a \(c_2\) alla data \(t\) |
📐 2. Prezzo di Valutazione
- Il resolver unificato è l'unico motore di valutazione:
MARKET → TRADE_AVG → CARRIED → MISSING. CARRIEDè l'ultima osservazione mantenuta (LOCF). Porta con sé i metadati di obsolescenzadays_back.estimated=Truesignifica origine TRADE. Una quotazione MARKET obsoleta mantenuta è obsoleta, non stimata.- I prezzi di valutazione rimangono nella valuta nativa; ogni consumatore converte in \(C^*\) alla data di valutazione \(t\).
- L'FX del costo di carico rimane ancorato alla data della transazione.
- La liquidità resta nella valuta in cui è stata registrata, broker per broker, ed è valutata al tasso di \(t\) (§5); ogni movimento di cassa resta registrato, e ogni flusso di cassa esterno entra nel capitale, al tasso della propria data.
- Il PMC non viene mai usato come prezzo di valutazione.
Vedi Risoluzione del prezzo per il contratto del resolver e la semantica della qualità dei dati.
📐 3. Stato della Posizione
Per ogni posizione \((a, b)\) con \(q(a,b,t) > 0\):
Dove \(w(a,b,t)\) è il Prezzo Medio di Carico (PMC) per la posizione \((a,b)\) alla data \(t\), mantenuto in \(C^*\) ai tassi storici (§4): il costo di carico non applica alcun tasso di cambio a \(t\), quindi per un asset estero l'effetto del tasso di cambio fa parte di \(\mathrm{UGL}\).
📐 4. Aggiornamento Iterativo del PMC
Mantenuto per posizione \((a,b)\) con stato del pool \((\hat{q}, \hat{c})\), il costo \(\hat{c}\) mantenuto in \(C^*\):
Acquisizione (quantità \(> 0\), importo \(P\) pagato nella valuta \(c\) alla data \(d\)):
\(P\) è la liquidità pagata per un acquisto, o il costo di carico per unità sovrascritto moltiplicato per \(q_{\text{tx}}\) per un trasferimento o una rettifica; \(\mathrm{fx}(C^*, C^*, d) = 1\). Quando non esiste un tasso a o prima di \(d\), o l'acquisizione non ha un costo di carico, la quantità viene registrata e il costo non viene registrato: il costo della posizione viene contrassegnato come incompleto invece di essere conteggiato come zero.
Riduzione (quantità \(< 0\)):
Split (collegato a un evento di split): \(\hat{q}\) cambia, \(\hat{c}\) no.
Ordinamento
All'interno della stessa data: le aggiunte vengono elaborate prima delle riduzioni. Garantisce che la VENDITA legga il PMC corretto includendo gli ACQUISTI dello stesso giorno.
📐 5. Aggregazione del Portafoglio
\(\mathrm{Cash}(t)\) è la liquidità di ciascun broker, mantenuta nelle valute in cui è stata registrata e valutata al tasso di \(t\):
dove \(N_{b,c}(t)\) è il saldo del broker \(b\) nella valuta \(c\) dopo i suoi movimenti con data uguale o precedente a \(t\), in proporzione alla quota di proprietà del broker, e \(\mathrm{fx}(c, C^*, t)\) è l'ultimo tasso disponibile alla data \(t\) o prima (\(1\) per \(c = C^*\)). Lo stesso termine compare nel NAV e nel Book, quindi l'effetto di cambio sulla liquidità si annulla nell'UGL: è registrato come risultato di cambio (§6) e appartiene al P&L totale.
📐 6. Modello di Liquidità a Tre Pool — Per Broker \((K_b, R_b, W)\)
Tre pool di accumulo tracciano la provenienza della liquidità. \(K\) e \(R\) sono mantenuti per broker \(b\); \(W\) è globale (esce completamente dal sistema).
| Pool | Ambito | Significato |
|---|---|---|
| \(K_b\) | Per broker | Capitale esterno ancora presso il broker \(b\) come liquidità |
| \(R_b\) | Per broker | Rendimenti generati ancora presso il broker \(b\) come liquidità |
| \(W\) | Globale | Rendimenti che hanno lasciato il sistema (nascosti, ripristinabili in caso di nuovo deposito) |
Proprietà chiave
Un acquisto sul broker \(b_1\) può consumare solo \(R_{b_1}\), mai \(R_{b_2}\). La liquidità non si teletrasporta tra broker — solo i trasferimenti espliciti spostano i saldi dei pool.
🔁 Regole di aggiornamento (per transazione sul broker \(b\), in ordine cronologico)
| Icona e Tipo | Formule di Aggiornamento | Logica e Descrizione |
|---|---|---|
DEPOSITO \(D > 0\) |
\(r = \min(D,\, W)\) \(R_b \mathrel{+}= r\) \(W \mathrel{-}= r\) \(K_b \mathrel{+}= D - r\) |
Ripristina prima i rendimenti precedentemente prelevati dal tracker globale \(W\), poi aggiunge il resto al capitale \(K_b\). |
PRELIEVO \(X > 0\) |
\(k = \min(X,\, K_b)\) \(K_b \mathrel{-}= k\) \(\rho = \min(X - k,\, R_b)\) \(R_b \mathrel{-}= \rho\) \(W \mathrel{+}= \rho\) |
Consuma prima il capitale \(K_b\), poi sposta i rendimenti rimanenti \(\rho\) al tracker globale \(W\). |
DIVIDENDO / INTERESSE \(I > 0\) |
\(R_b \mathrel{+}= I\) | I rendimenti aumentano direttamente il pool dei rendimenti \(R_b\). |
COMMISSIONE / IMPOSTA \(F > 0\) |
\(R_b \mathrel{-}= F\) \(\text{if } R_b < 0\text{: } K_b \mathrel{+}= R_b,\; R_b = 0\) |
Consuma prima i rendimenti \(R_b\); se \(R_b\) diventa negativo, attinge dal capitale \(K_b\). |
ACQUISTO \(B > 0\) |
\(\rho = \min(B,\, R_b)\) \(R_b \mathrel{-}= \rho\) \(K_b \mathrel{-}= (B - \rho)\) |
Consuma prima i rendimenti \(R_b\), poi attinge il resto dal capitale \(K_b\). |
VENDITA |
\(G = P - C\) \(K_b \mathrel{+}= C\) \(R_b \mathrel{+}= G\) \(\text{if } R_b < 0\text{: } K_b \mathrel{+}= R_b, \quad R_b = 0\) |
Il costo di carico $C = |
GIROCONTO (Interno, \(s \to d\), \(X > 0\)) |
Tratta di partenza (\(s\)): \(\rho = \min(X,\, R_s)\) \(R_s \mathrel{-}= \rho\) \(\kappa = X - \rho\) \(K_s \mathrel{-}= \kappa\) Tratta di arrivo (\(d\)): \(K_d \mathrel{+}= \kappa\) \(R_d \mathrel{+}= \rho\) |
I giroconti interni spostano le allocazioni dei pool (\(R_s \to R_d\), \(K_s \to K_d\)) in proporzione al saldo di partenza. Il tracker globale \(W\) non viene mai toccato (il capitale rimane all'interno del sistema). |
Se le date di partenza e arrivo differiscono, il giroconto è in transito: sottratto da \(s\) il giorno di partenza, aggiunto a \(d\) il giorno di arrivo. Tra queste date, \(\sum K_b + \sum R_b < \mathrm{Cash}_{\text{like}}\) dell'importo in transito — gestito dalla riconciliazione proporzionale.
💱 Risultato di cambio sulla liquidità in valuta
Ogni movimento di cassa entra nella liquidità del broker, e nei suoi pool, al tasso della propria data; il saldo detenuto in seguito segue il tasso (§5). In ogni giorno \(t\) in cui cambia il tasso di una valuta estera detenuta come liquidità in \(S\) — compreso il suo primo tasso noto — dopo i movimenti di cassa di quel giorno e prima che le transazioni di quel giorno aggiornino i pool, ciascun broker \(b\) che detiene liquidità in valuta estera viene rivalutato:
\(\mathrm{Cash}^{\text{replay}}_b(t)\) è la liquidità che il replay porta per \(b\): il suo valore alla rivalutazione precedente più ogni movimento successivo al tasso della propria data. Un guadagno va ai rendimenti; una perdita consuma prima i rendimenti e poi il capitale, esattamente come una COMMISSIONE. La base del capitale non si muove: un risultato di cambio è un risultato, non un apporto, quindi è nel NAV, nel P&L totale, nel ROI, nel TWRR e nel MWRR, mai nel capitale versato.
🧮 Aggregazione per l'output
⚖️ Invariante di riconciliazione
Entrambi i pool vengono prima limitati a zero per ciascun broker. Se i pool non sono vuoti e lo scostamento supera ancora \(0.01\), i pool sommati vengono ridimensionati a \(\mathrm{Cash}_{\text{like}}\), la liquidità più la liquidità in transito — un ridimensionamento aggregato, non per broker, con ogni risultato limitato inferiormente a zero:
Altrimenti \(\mathrm{CashFromCapital}(t) = \min\bigl(\sum_b K_b(t),\, \mathrm{Cash}_{\text{like}}(t)\bigr)\) e \(\mathrm{CashFromReturns}\) è il resto, limitato inferiormente a zero. I risultati di cambio sulla liquidità ferma sono registrati nei pool (sopra), quindi lo scostamento che resta viene dalla tempistica in transito: la liquidità in transito — e il movimento del suo tasso di cambio mentre viaggia — non è nei pool di alcun broker.
📐 7. Contributo del Periodo
Per il periodo \([t_0, t_1]\), per posizione \((a,b)\):
Insieme delle posizioni contributive:
Il P&L periodo a livello di portafoglio espone anche un residuo:
Poiché l'UGL non può contenere il risultato di cambio sulla liquidità (§5), Other si divide nel risultato di cambio di ciascun broker sul periodo e in ciò che resta:
Commissioni/redditi non allocati senza asset_id sono raggruppati per broker come altri effetti del periodo, e così \(\mathrm{FXonCash}_b\): una riga per ogni broker che detiene liquidità in valuta estera, mostrata quando il suo risultato non è zero. Vedi P&L periodo — Effetto cambio sulla liquidità.
📐 8. Plusvalenza/Minusvalenza Realizzata
Alla VENDITA di \(|q_s|\) unità dalla posizione \((a,b)\) alla data \(t\):
Dove \(w_{\text{pre}}\) è il PMC in \(C^*\) prima della riduzione del pool (stesso valore usato dalla regola di VENDITA a 3 pool sopra): le unità vendute escono al loro costo storico, senza conversione alla data di vendita. Una vendita i cui proventi non possono essere convertiti, o che proviene da una posizione con costo incompleto, è esclusa dal P&L realizzato.
📐 9. Architettura Pre-Frame / Frame
| Fase | Intervallo di date | Calcola |
|---|---|---|
| Pre-frame | \([t_{\mathrm{first}},\ t_0)\) | Liquidità, quantità, PMC, pool — nessuna valutazione di mercato |
| Frame | \([t_0,\ t_1]\) | Giornaliero completo: prezzi, FX, stati delle posizioni, stati del portafoglio |
Le transazioni pre-frame aggiornano gli accumulatori (registro di cassa, pool PMC, K/R/W a 3 pool) senza alcuna valutazione di mercato: nessun prezzo viene letto e nessuna posizione viene valutata. Ogni movimento è convertito al tasso della propria data, come nel frame, e in ogni giorno in cui cambia il tasso di una valuta estera detenuta, la liquidità viene rivalutata al tasso di quel giorno e il risultato di cambio entra nei pool (§6), così i pool sono corretti a \(t_0\). Ciò consente un caching efficiente basato su intervalli.
📐 10. Metriche di Performance (Livello 2)
Calcolate dopo gli stati giornalieri, come passaggio separato:
| Metrica | Formula | Riferimento |
|---|---|---|
| P&L Totale | \(\mathrm{NAV}(t) - \text{CapitalBaseline}(t)\) | Capitale Versato |
| P&L periodo | \(\mathrm{NAV}(t_1) - \mathrm{NAV}(t_0) - \text{ECF}_{[t_0,t_1]}\) | P&L periodo |
| TWRR | \(\prod_i (1 + r_i) - 1\) (catena di sotto-periodi) | TWRR |
| MWRR | XIRR risolvendo \(\sum \frac{CF_i}{(1+r)^{d_i/365}} = 0\) | MWRR |
| ROI Semplice | \((\mathrm{NAV} - \text{NetInvested}) / \text{NetInvested}\) | ROI |
| Rendimento annualizzato netto | \((1+r_{\mathrm{net}})^{365/d}-1\), soppresso sotto i 30 giorni | Rendimento Annualizzato Netto |
| Rendimento sul costo | Reddito lordo da transazioni degli ultimi 365 giorni per unità storica ammissibile, diviso per il PMC unitario residuo a \(t_1\) | Rendimento sul costo |
| Effetto timing | \(\text{MWRR}_{\text{cum}} - \text{TWRR}_{\text{cum}}\) | Effetto timing |
🔗 Correlati
- 💼 NAV — valutazione istantanea
- 🧭 Risoluzione del prezzo — resolver di valutazione unificato
- 📈 Rendimento Annualizzato Netto — definizioni di CAGR per posizioni, periodo e FIFO
- 💸 Rendimento sul costo — reddito lordo registrato degli ultimi 365 giorni rispetto al PMC unitario residuo
- 📖 Valore contabile — aggregato del costo di carico
- 📊 P&L periodo — guadagno/perdita su finestra con contributo
- 💸 Capitale Versato — dettagli dei 3 pool ed esempi svolti
- 📈 PMC — metodo del costo iterativo
- 📈 Panoramica delle Metriche di Performance — tutte le metriche di performance a colpo d'occhio