SPB Git forge

spb/wp14_uqo

Public
2commits 1branches 1releases
909.0 KBsize
maindefault branch
57 min agolast push
Python 57% TeX 42.9%
16.9 KB · 373 lines latex
Raw Blame History
1\documentclass[11pt,a4paper]{article}23\usepackage[utf8]{inputenc}4\usepackage[T1]{fontenc}5\usepackage[french]{babel}6\usepackage{lmodern}7\usepackage{amsmath,amssymb}8\usepackage{booktabs}9\usepackage{longtable}10\usepackage{array}11\usepackage{geometry}12\usepackage{xcolor}13\usepackage{enumitem}14\usepackage{hyperref}15\usepackage{fancyhdr}1617\geometry{margin=2.4cm}18\hypersetup{colorlinks=true, linkcolor=blue!55!black, urlcolor=blue!55!black,19  citecolor=blue!55!black}2021\newcommand{\code}[1]{\texttt{\small #1}}22\renewcommand{\arraystretch}{1.25}2324\pagestyle{fancy}25\fancyhf{}26\lhead{\small Modèle hédonique de prix — Québec}27\rhead{\small\thepage}28\renewcommand{\headrulewidth}{0.4pt}2930\title{\textbf{Méthodologie}\\[2mm]31\large Modèle hédonique de prix des maisons (Québec)\\[1mm]32\normalsize Realtor.ca $+$ DuProprio $\rightarrow$ nettoyage $\rightarrow$ ingénierie33de variables (règles $+$ LLM $+$ vision) $\rightarrow$ régression hédonique34log-linéaire à effets fixes}35\author{}36\date{Données extraites le 3 juillet 2026}3738\begin{document}39\maketitle40\thispagestyle{fancy}4142\begin{abstract}43\noindent Ce document décrit la méthodologie complète de construction d'un modèle44hédonique de prix pour les maisons unifamiliales et maisons en rangée du Québec.45Le pipeline combine deux jeux de données d'annonces immobilières, un nettoyage des46valeurs aberrantes fondé sur des règles, une ingénierie de variables à quatre47origines (règles déterministes, extraction de texte par grand modèle de langage,48analyse d'images par modèle de vision, effets fixes géographiques) et une49estimation par moindres carrés ordinaires du logarithme du prix avec erreurs-types50robustes à l'hétéroscédasticité.51\end{abstract}5253\tableofcontents54\bigskip5556%======================================================================57\section{Origine des données}5859\begin{longtable}{@{}p{2.4cm}p{5.2cm}rp{4.6cm}@{}}60\toprule61\textbf{Source} & \textbf{Fichier} & \textbf{Nb} & \textbf{Nature}\\62\midrule63\endhead64Realtor.ca & \code{dataset\_realtor-\dots.json} (161 Mo) & 27\,302 &65Annonces MLS via crawler Apify\\66DuProprio & \code{dataset\_duproprio-\dots.json} (87 Mo) & 7\,693 &67Annonces de vente sans intermédiaire (Apify)\\68\bottomrule69\end{longtable}7071\begin{itemize}[leftmargin=1.2em]72  \item \textbf{Collecte} : scrapers Apify, extraction le \textbf{2026-07-03}. Chaque73  enregistrement est un objet JSON structuré.74  \item \textbf{Champs communs} : \code{source}, \code{url}, \code{listingId},75  \code{title}, \code{price}/\code{priceNumber}, \code{currency},76  \code{address\{...\}}, \code{property\{...\}}, \code{features[]},77  \code{description}, \code{images[]}, \code{scrapedAt}.78  \item \textbf{Spécificités} :79  \begin{itemize}[leftmargin=1.2em]80    \item Realtor : \code{buildingType}, \code{storeys}, \code{yearBuilt},81    \code{parkingSpaces}, \textbf{\code{rooms[]}} (dimensions par pièce) ;82    pas de coordonnées GPS ; images sans légende utile.83    \item DuProprio : \code{type}, \code{levels},84    \textbf{\code{coordinates}} (7\,691 présentes) ; images \textbf{avec légendes}85    (\emph{Kitchen}, etc.) ; pas de \code{rooms}.86  \end{itemize}87  \item \textbf{Instantané transversal} (une seule date) : pas de dimension88  temporelle, donc pas d'effet fixe temporel requis.89\end{itemize}9091\noindent\textbf{Identifiant unique} : \code{uid = source + ":" + listingId}92(évite toute collision entre les deux espaces d'identifiants).9394%======================================================================95\section{Construction du dataset «~maisons~»}9697\begin{enumerate}[leftmargin=1.4em]98  \item \textbf{Fusion} des deux tableaux JSON (schéma harmonisé).99  \item \textbf{Définition de «~maison~»} (unifamiliales $+$ maisons en rangée) :100  \begin{itemize}[leftmargin=1.2em]101    \item Realtor : \code{buildingType} $\in \{$House, Row/Townhouse$\}$ ;102    \item DuProprio : \code{type} $\in \{$Home, Bungalow, Semi Detached,103    Intergenerational, Country Home, Cottage, Villa, Townhouse$\}$ ;104    \item \emph{Exclus} : condos, plex (duplex$\rightarrow$quintuplex),105    terrains/lots, fermes, commercial, maisons mobiles.106  \end{itemize}107  \item \textbf{Filtre prix présent} : \code{priceNumber} non nul et $>0$.108\end{enumerate}109110\noindent$\rightarrow$ \textbf{19\,273 maisons avec prix} (15\,470 Realtor111$+$ 3\,803 DuProprio).112113%======================================================================114\section{Nettoyage des valeurs aberrantes}115116Les prix extraits contiennent des erreurs d'analyse syntaxique (minimum117observé 899~\$, maximum 368~G\$). Règles appliquées :118119\begin{longtable}{@{}p{3.0cm}p{6.2cm}p{5.2cm}@{}}120\toprule121\textbf{Variable} & \textbf{Règle} & \textbf{Justification}\\122\midrule123\endhead124Prix & garder \textbf{50\,k\$ -- 15\,M\$} & plage plausible au QC ; retire loyers125mal analysés et concaténations\\126Surface habitable & 300 -- 20\,000 ft$^2$ (sinon $\rightarrow$ manquant) &127valeurs physiquement possibles\\128Terrain & 200 -- 5\,000\,000 ft$^2$ (sinon $\rightarrow$ manquant) & idem\\129Chambres / sdb & 0--15 / 0--12 (sinon $\rightarrow$ manquant) & plafonds réalistes\\130Prix/pied$^2$ & garder \textbf{P0{,}5 -- P99{,}5} ($\approx 73$--$1276~\$$/ft$^2$) &131retire les erreurs résiduelles de prix ou surface\\132\bottomrule133\end{longtable}134135\noindent$\rightarrow$ \textbf{19\,115 maisons} conservées (158 retirées).136137\paragraph{Principe.} On \emph{borne} plutôt que de supprimer quand une seule138variable est aberrante : la variable est mise à \emph{manquant} puis imputée, pour139ne pas perdre l'observation entière.140141%======================================================================142\section{Construction des variables}143144\subsection{Variable cible}145\[146\code{ln\_price} = \ln(\code{priceNumber})147\]148La transformation logarithmique rend la distribution symétrique, linéarise les149effets multiplicatifs et donne des coefficients interprétables en pourcentage150d'impact sur le prix.151152\subsection{Variables structurelles (règles déterministes)}153\begin{itemize}[leftmargin=1.2em]154  \item \textbf{Surface \& terrain} : analyse d'unités hétérogènes, tout converti en155  \textbf{pieds carrés} : \code{"1535 sqft"}, \code{"1,333.2 ft²"},156  \code{"11 561.52 ft²"} (séparateurs de milliers variés),157  \code{"961.6 m2"} ($\times 10{,}7639$).158  \item \textbf{Reconstruction de surface via les pièces (Realtor)} : dimensions159  \code{"23 ft ,4 in x 13 ft ,8 in"} $\rightarrow$ pieds décimaux $\rightarrow$ aire,160  sommées sur toutes les pièces. Calibration sur le recouvrement (ratio médian161  surface réelle / somme des pièces $\approx 0{,}98$) pour combler162  \code{squareFeet} manquant.163  \item \textbf{Autres} : \code{beds}, \code{baths}, \code{parking},164  \code{storeys}/\code{levels}, \code{age} $= 2026 - \code{yearBuilt}$ (avec165  \code{age}$^2$ pour la courbure), drapeaux \code{has\_*} marquant les valeurs166  imputées.167\end{itemize}168169\subsection{Aménités (règles par mots-clés bilingues)}17017 variables indicatrices détectées dans \code{features[]} $+$ \code{description}171$+$ \code{title} (FR/EN) : piscine, bord de l'eau, garage, foyer, climatisation/172thermopompe, sous-sol fini, cul-de-sac, golf, ski, proximité parc/école/autoroute/173transport, absence de voisin arrière.174175\subsection{Détail des pièces (Realtor)}176Nombre de pièces, nombre de niveaux, chambre principale, sous-sol, bureau, salle177familiale, atelier, cellier à vin, solarium, mezzanine, bibliothèque, buanderie.178179\subsection{Signaux de mise en marché}180Nombre de photos (\code{n\_images}, écrêté à 60), présence de visite virtuelle —181indicateurs indirects de gamme et de qualité de l'annonce.182183\subsection{Variables géographiques (effets fixes)}184\begin{itemize}[leftmargin=1.2em]185  \item \textbf{Ville} nettoyée (Realtor : retrait du quartier entre parenthèses ;186  minuscules ; normalisation). Villes avec $\ge 20$ annonces $\rightarrow$187  indicatrice propre, les rares $\rightarrow$ \code{\_\_other\_\_}188  ($\approx 194$ villes en effets fixes).189  \item \textbf{Type de propriété} harmonisé, regroupé si $<30$ annonces.190  \item \textbf{Source} (Realtor/DuProprio) $\rightarrow$ indicatrice captant les191  différences systématiques entre plateformes.192\end{itemize}193194\subsection{Imputation}195Valeurs manquantes après nettoyage : imputées par \textbf{médiane par type de196propriété} (puis médiane globale), \textbf{avec un drapeau \code{has\_*}} pour que197le modèle distingue valeur observée et valeur imputée.198199%======================================================================200\section{Mécanismes d'IA pour l'ingénierie de variables}201202Deux couches d'IA extraient des variables impossibles à obtenir par règles~: l'une203depuis le texte, l'autre depuis les images.204205\subsection{Extraction de specs depuis la description --- GPT-4o-mini}206\begin{itemize}[leftmargin=1.2em]207  \item \textbf{But} : transformer la description libre en 20 attributs structurés208  (état~: à rénover$\rightarrow$neuf ; clé en main ; cuisine/sdb rénovée ;209  revêtements de sol ; comptoirs quartz/granit ; chauffage ; vue sur l'eau ;210  revenus locatifs ; grand terrain ; secteur tranquille ; mots-clés de vente).211  \item \textbf{Mécanisme} : appel \emph{Chat Completions} avec212  \code{response\_format = json\_schema} \textbf{strict} (schéma imposé,213  énumérations fermées) $\rightarrow$ sortie JSON valide garantie, sans analyse214  fragile. \code{temperature = 0} (déterminisme). Instruction système : extracteur215  factuel, uniquement d'après le texte ; absence $\rightarrow$ false/inconnu/[].216  \item \textbf{Ingénierie} : $\sim$600 tokens en entrée / $\sim$110 en sortie par217  annonce ; \textbf{parallèle} (24 fils), \textbf{résumable} (cache218  \code{specs.jsonl}, clé \code{uid}), \textbf{réessais} exponentiels sur 429/5xx.219  \item \textbf{Coût / temps} : $\sim$\$3 pour $\sim$19\,k annonces.220\end{itemize}221222\subsection{Attributs visuels de façade --- Claude Haiku 4.5 (vision)}223\begin{itemize}[leftmargin=1.2em]224  \item \textbf{But} : lire ce que le texte ne dit pas --- état visuel réel,225  attrait extérieur (\emph{curb appeal}), niveau de rénovation, matériaux,226  aménagement paysager, cadre (urbain/banlieue/rural/bord d'eau/boisé), indice de227  luxe, qualité de la photo.228  \item \textbf{Sélection d'image} : une photo/annonce $=$ la façade. Realtor229  $\rightarrow$ 1\up{re} photo ; DuProprio $\rightarrow$ photo dont la légende est230  l'adresse (pas une pièce), par exclusion de mots-clés de pièces.231  \item \textbf{Mécanisme} : \emph{Messages API}, image passée par \textbf{URL}232  (\code{source.type = url}, sans téléchargement),233  \code{output\_config.format = json\_schema} (12 attributs, énumérations fermées).234  Instruction système : évaluateur objectif ; scores fondés sur des critères235  concrets (surfaces, matériaux, aménagement), pas sur un goût personnel.236  \item \textbf{Ingénierie} : $\sim$2\,470 tokens en entrée / $\sim$100 en sortie237  par image ; \textbf{parallèle} (16 fils), \textbf{résumable} (cache238  \code{facade\_specs.jsonl}), \textbf{réessais} sur 429/5xx/529.239  \item \textbf{Coût / temps} : $\sim$\$57 pour $\sim$19\,k images.240  \item \textbf{Choix de Haiku} : modèle de vision le moins cher et rapide,241  suffisant pour de la classification d'attributs concrets.242\end{itemize}243244\subsection{Rôle central du JSON structuré strict}245Le schéma imposé (types $+$ \code{enum} $+$ champs requis $+$246\code{additionalProperties:false}) fait valider la sortie \textbf{au niveau de247l'API}~: le modèle renvoie exactement les champs attendus, dans le bon domaine de248valeurs. On obtient des variables directement tabulables et reproductibles, sans249post-traitement de texte libre.250251\subsection{Intégration au dataset}252Les sorties des modèles (clé \code{uid}) sont converties en variables numériques~:253booléens $\rightarrow$ 0/1, état $\rightarrow$ score ordinal 0--5, revêtements254$\rightarrow$ indicatrices (bois franc, quartz/granit), vue $\rightarrow$255indicatrice eau, etc., avec un drapeau \code{has\_gpt} / \code{is\_exterior}256marquant la disponibilité.257258%======================================================================259\section{Modèle économétrique}260261\subsection{Spécification --- hédonique log-linéaire à effets fixes}262\begin{equation}263\ln(P_i) = \alpha + \beta\,\ln(\text{surface}_i) + \gamma\,\ln(\text{terrain}_i)264+ \sum_k \delta_k X_{ki}265+ \sum_c \lambda_c\,\mathbb{1}[\text{ville}_i=c]266+ \varepsilon_i267\end{equation}268269\begin{itemize}[leftmargin=1.2em]270  \item \textbf{Log--log} sur surface et terrain $\rightarrow$ coefficients $=$271  \textbf{élasticités} (\% de prix par \% de surface).272  \item \textbf{Log--niveau} sur le reste $\rightarrow$ un coefficient $b$ vaut273  $\approx (e^{b}-1)\times 100$~\% d'impact sur le prix.274  \item \textbf{Effets fixes ville} ($\lambda_c$) : absorbent le différentiel de275  localisation (premier déterminant du prix) ; chaque coefficient $=$ prime/décote276  de la ville vs la référence.277  \item \textbf{Effets fixes} type de propriété et source.278\end{itemize}279280\subsection{Double spécification (couverture vs richesse)}281Realtor ne rapporte \code{squareFeet} que pour $\sim$38~\% des annonces, d'où deux282modèles et des prédictions combinées~:283\begin{itemize}[leftmargin=1.2em]284  \item \textbf{Modèle A (riche)} : inclut $\ln(\text{surface})$, estimé sur les285  biens à surface \emph{mesurée} (réelle ou reconstruite via les pièces). Meilleur286  ajustement.287  \item \textbf{Modèle B (large)} : sans surface, estimé sur \emph{toutes} les288  maisons $\rightarrow$ price celles sans surface (beds/baths/terrain/pièces $+$289  specs).290  \item \textbf{Prédiction finale} : A si surface mesurée, sinon B.291\end{itemize}292293\subsection{Estimation et inférence}294\begin{itemize}[leftmargin=1.2em]295  \item \textbf{Moindres carrés ordinaires} sur \code{ln\_price}.296  \item \textbf{Erreurs-types robustes à l'hétéroscédasticité HC3} (les résidus297  immobiliers sont hétéroscédastiques ; HC3 est conservateur en échantillon298  moyen).299  \item \textbf{Correction du biais de rétrotransformation} :300  \[301  \hat{P} = e^{\widehat{\ln P}} \times e^{\hat\sigma^2/2}302  \]303  (correction normale de Duan) --- sinon $e^{\widehat{\ln P}}$ sous-estime304  systématiquement le niveau de prix.305\end{itemize}306307\subsection{Interprétation}308Coefficients rapportés en \textbf{\% d'impact prix} $+$ significativité (p-values309sur SE HC3). Effets fixes ville présentés comme primes de localisation.310311%======================================================================312\section{Statistiques et diagnostics}313314\begin{longtable}{@{}p{5.2cm}p{9.4cm}@{}}315\toprule316\textbf{Indicateur} & \textbf{Signification}\\317\midrule318\endhead319$R^2$ / $R^2$ ajusté & part de variance de \code{ln\_price} expliquée\\320Écart-type des résidus (log) & $\rightarrow$ erreur typique en \% $=(e^{\sigma}-1)\times100$\\321Erreur absolue médiane & $|\,$prix réel $/$ prix prédit $-1\,|$ médian\\322\% à $\pm15$~\% / $\pm25$~\% & part des prédictions dans la fourchette\\323\code{resid\_pct} par annonce & surprix/sous-prix vs modèle324$\rightarrow$ repère aubaines et surévaluations\\325\bottomrule326\end{longtable}327328\noindent Progression observée : v2 (structurel) $R^2\approx0{,}70$329$\rightarrow$ v3 ($+$ pièces/photos) $R^2\approx0{,}72$330$\rightarrow$ v4 ($+$ specs GPT) $\rightarrow$ v5 ($+$ vision) attendu.331332%======================================================================333\section{Limites et biais}334335\begin{itemize}[leftmargin=1.2em]336  \item \textbf{Endogénéité / non-causalité} : de belles photos ou des specs riches337  corrèlent avec des courtiers haut de gamme et des biens chers $\rightarrow$338  coefficients \emph{prédictifs}, pas causaux.339  \item \textbf{Biais de sélection} : uniquement des biens \emph{en vente} (prix340  demandé, pas prix de transaction) ; les biens sans surface/pièces sont non341  aléatoires (annonces moins complètes).342  \item \textbf{Imputation} : les médianes par type réduisent la variance des343  variables imputées (atténuation possible des coefficients), d'où les drapeaux344  \code{has\_*}.345  \item \textbf{Extraction LLM} : erreurs/hallucinations possibles ;346  \code{temperature=0} $+$ schéma strict $+$ énumérations fermées les limitent,347  sans validation humaine systématique. La vision juge sur \emph{une seule} photo.348  \item \textbf{Instantané unique} : pas de dynamique de marché ; primes de349  localisation figées au 2026-07-03.350  \item \textbf{Couverture géographique} : villes $<20$ annonces regroupées en351  \code{\_\_other\_\_}.352\end{itemize}353354%======================================================================355\section{Fichiers produits}356357\begin{longtable}{@{}p{5.4cm}p{9.2cm}@{}}358\toprule359\textbf{Fichier} & \textbf{Contenu}\\360\midrule361\endhead362\code{hedonic.py}, \code{hedonic\_v4.py} & pipelines reproductibles (nettoyage $+$363modèles)\\364\code{extract\_specs.py}, \code{facade\_vision.py} & extracteurs LLM (texte /365vision), parallèles et résumables\\366\code{specs.jsonl}, \code{facade\_specs.jsonl} & sorties LLM brutes (clé \code{uid})\\367\code{maisons\_hedonic*.csv} & dataset final $+$ prix prédit $+$ \code{resid\_pct}\\368\code{hedonic\_*\_summary.txt} & sorties statistiques complètes\\369\bottomrule370\end{longtable}371372\end{document}373