Python 64.6%
TeX 23.3%
HTML 11.6%
Makefile 0.5%
1# Changelog — scientific revision of UQO WP 4 (editorial board, 2026-10-17)23Reference state: tag `pre-revision-20261017`, `docs/main_pre-revision-20261017.pdf`. All original files are preserved in git.4Every number of v1.1 is produced by `scripts/10_revision_reanalysis.py` and written to `results/tables/rev_*.tex|json` and5`paper/figures/rev_*.pdf`; no table is typed by hand. Key numbers quoted in the text are in `results/tables/rev_key_numbers.json`.67## 1. Data provenance and preparation89| # | Where | Before (v1.0) | After (v1.1) | Why / evidence |10|---|---|---|---|---|11| 1 | §2.1, README, `data/raw/README.md` | "Inside Airbnb extract, listings.csv, amenity lists, host profiles, descriptions, calendar" | Scrape of Airbnb search-result cards (19 fields; no room type, host ID, amenity list, cleaning fee, minimum stay); file without timestamp, early 2026, same 5,000 listings as WP 5 | `src/data_loader.py` schema; `data_inspection.txt` of WP 5; Guest Favourite badge and "quality_score" do not exist in Inside Airbnb |12| 2 | data | raw `cleaned_dataset_sample.csv` absent from the repo and from the laptop and cluster | `data/processed/airbnb_clean_wp5.parquet` (227 KB) copied from WP 5 (`02_clean_airbnb.py`: price p1/p99 winsorised, rating median-imputed, reviews NaN→0, city names standardised) and committed; the only local copy of the data | search of laptop + 6 cluster nodes, 2026-10-17 |13| 3 | §2.1 | rating "converted from 0–100 to 0–5"; 810 missing ratings | ratings already 0–5; 456 of 3,456 priced listings unrated (parsed from title: no star); 37 German-locale ratings truncated to 4.0 by a decimal-comma error, repaired from the title | script §1, `KEY.n_unrated`, `KEY.n_rating_truncated_fixed` |14| 4 | §2.1 | bathrooms field used as is (478 zeros) | 433 zero-bathroom records repaired from the title ("1 shared bath", "1 private bath"), 32 half baths = 0.5; 161 studios recoded to one sleeping room + studio indicator; 46 bedroom counts recovered from titles | the scraper stored 0 whenever the bath descriptor was qualified; `KEY.n_bathrooms_recovered = 465` |15| 5 | §2 | "Entire home 48.1 %, private room 35.5 %, shared room 16.4 %" | removed — these were property-type groups relabelled in `src/feature_engineering.py` (`Rental unit` → "private room", `Other` → "shared room"); room type is not observed | code inspection |16| 6 | §2, §3, §4 | six "amenity indices" (luxury, business travel, family comfort, leisure, remote work, richness) | removed — `src/amenities.py::_proxy_indices_from_count` adds N(0, 0.05) noise to the normalised count; only `ln(1 + amenities)` is used | code inspection; integrity |17| 7 | §2, §3 | "multi-listing host" (duplicated titles), `host_professional_dummy` (constant 0), reputation score, cleanliness premium, "location rating premium", "quality score" | removed; quality score shown to be a function of reviews/badges/photos (R² 0.63) | code inspection; script §1 |18| 8 | §2, §4 | TF-IDF/SVD "text embeddings" of the card title (templated: category · city · rating · bedrooms · beds · baths) | removed; the title is parsed into its fields instead (category, rating, beds, bath type) | the "text" effect was a re-encoding of city and size |1920## 2. The price field (main correction)2122| # | Where | Before | After | Evidence |23|---|---|---|---|---|24| 9 | §2.2, Fig. 1, Table 1 | nightly price mean \$1,115, median \$219, P75 \$1,139, Winsorisation \$38–\$10,822; no comment | bimodal log price (mixture modes ≈ \$150 and ≈ \$2,500); 915 listings (26.5 %) above \$1,000; median ratio above/below \$1,000 by bedrooms 16–19 ×; interpretation: total stay price (≈ 23 nights) captured for part of the sample | `rev_price_regimes.tex`, `rev_fig_logprice_mixture.pdf`, `KEY.mix` |25| 10 | §2.2, §3.6, Table 2 | — | two-regime mixture of hedonic regressions (EM, common slopes, δ̂ = 3.154, σ̂₀ = 0.493, σ̂₁ = 0.568, logistic regime equation); 976 stay-regime listings (83 of them ≤ \$1,000), 22 nightly listings > \$1,000, 7 ambiguous; analysis sample N = 2,480 | `rev_mixture.tex`, `KEY.mixreg` |26| 11 | all result tables | N = 3,412 / 2,861 / 1,906 (listwise + neighbour-within-500 m selection) | N = 2,480 in every specification | script |2728## 3. Models and results (old → new)2930| # | Where | Before | After | Evidence |31|---|---|---|---|---|32| 12 | Table 4 (nested OLS) | M1–M9, 15–50 "parameters" (60 rows in appendix, duplicates, pinv), R² 0.052 → 0.274 | M1–M5, 10–21 regressors + FE, R² 0.443 → 0.509, adj. 0.440 → 0.495, RMSE 0.506 → 0.475; HC3 and cluster SEs | `rev_ols_nested.tex` |33| 13 | §4.3 | bedrooms +212.9 % (β = 1.141), log bedrooms −87 % | ln bedrooms elasticity 0.160 (HC3 0.042), ln(1+bathrooms) 0.437 (0.070), ln guests 0.331 (0.037), shared bath −0.385 (0.053) | id. |34| 14 | §4.5 | rating β = 1.052 → "11.1 % per 0.1 point"; "has reviews" β = 9.511 | rating 0.337 per point among rated listings (≈ 3.4 % per 0.1), rated indicator −0.041 n.s., ln reviews 0.015 n.s., Superhost 0.023 n.s., Guest Favourite −0.035 n.s. | id. |35| 15 | §4.4 | amenity richness −23.6 %, business travel −68.5 % | removed (fabricated regressors); ln(1+amenities) 0.094 (0.038), ln(1+photos) 0.087 (0.022), pets −0.044 (0.023) | id. |36| 16 | §4.6 | latitude −8.6 %, density 500 m −0.8 %/listing, density 1 km +0.3 %, "local average price" +0.025 %, spatial cluster −1.3 % | ln(1+km to centre) −0.035 (0.019) with FE, ln(1+listings within 1 km) 0.064 (0.013); no neighbour-price regressor (treated by the SAR instead) | id. |37| 17 | Table 7 (quantiles) | 16 covariates incl. three collinear "room-type" dummies (≈ 1.0 each), pseudo-R² 0.10 → 0.02 | M5 regressors + FE at five quantiles; pseudo-R² 0.278 → 0.405; bootstrap tests of τ = 0.9 − τ = 0.1 differences | `rev_quantile.tex`, `KEY.iq_diff_90_10` |38| 18 | §4.10 (spatial) | no estimate reported (spreg absent; fallbacks) | Moran's I, SAR/SEM/SDM by ML (k = 5; k = 10 check), LR test, LeSage–Pace impacts with simulated SEs | `rev_spatial.tex`, `rev_impacts.tex`, `KEY.moran`, `KEY.spatial` |39| 19 | Table 8 (ML) | random 80/20 split, N_test = 382; "CatBoost" = sklearn GBR; "GAM" = polynomial; MAPE on log prices (14.3 %) | 5-fold random and spatially blocked CV (20 blocks) for OLS-M5, elastic net, RF, GBM, XGBoost, LightGBM; R², RMSE, MAE (log) and MdAPE (price scale); CatBoost and GAM dropped (packages absent, no fallback relabelling) | `rev_ml_cv.tex` |40| 20 | §4.9 (SHAP) | claimed; never computed (permutation fallback, no table) | exact TreeExplainer SHAP on XGBoost; importance table and beeswarm | `rev_shap_importance.tex`, `rev_fig_shap.pdf` |41| 21 | Table 9 (decomposition) | arithmetically impossible (predicted mean 3.99 vs 5.87; intercept 0; two blocks 0) | removed (not a result); block F-tests reported instead | `KEY.ftests_M5` |42| 22 | §5 | property-type subsamples labelled "room type"; regressions within price segments (conditioning on y); "Ultra-Luxury > \$1,000" = stay regime; adj. R² 0.08–0.10 | new robustness table (regime cut-offs 0.25/0.75, \$600/\$1,000 rules, full sample, weighting by 1 − p̂, hotel exclusion, rated only, Montreal/outside, trimming, 60-cell FE) | `rev_robustness.tex` |43| 23 | Figures 1–8 | produced on the contaminated sample; two of them (price distributions) displayed the bimodality without comment | Fig. 1 mixture; Fig. 2 price by category; Fig. 3 map; Fig. 4 partial relationships; Fig. 5 quantile coefficients; Fig. 6 SHAP | `paper/figures/rev_*.pdf` |44| 24 | main.tex | version 1.0, May 2026; JEL C21, C31, C45, C58, L83, R31, R33 | version 1.1, October 2026; JEL C21, C31, C45, L83, R31, Z30; keywords harmonised ("hedonic price function", "implicit prices") | HARMONISATION.md |4546## 4. References4748Removed 3 (Chattopadhyay & Machemehl 2006 unverifiable; Dogru & Pekin 2017 grey literature; Apley & Zhu 2020 unused).49Corrected 5 (Chen & Xie year 2017 and key; Magno et al. third author Ugolini; Gibbs et al. hedonic paper JTTM 35(1) added50as the source of the amenity result; Pérez-Sánchez and Zhang given names). Added 32, all verified on Crossref51(`api.crossref.org/works?query.bibliographic=…` and DOI lookups, 2026-10-17; Halvorsen–Palmquist 1980 and Kennedy 1981 verified52through RePEc). Full list with DOIs in `docs/REVIEW-REPORT.md` §4. Total 21 → 50.5354## 5. Re-analyses executed5556| Script | What | Runtime | Outputs |57|---|---|---|---|58| `scripts/10_revision_reanalysis.py` | title parsing and repairs; marginal mixture; regression mixture (EM); descriptives; OLS M1–M5 (HC3, cluster); VIF; block F-tests; QR (5 τ) + paired bootstrap (B = 100); Moran's I; SAR/SEM/SDM ML + impacts; 5-fold random/blocked CV of 6 models; SHAP; 12-variant robustness; 6 figures | ≈ 9 min on the laptop (bootstrap ≈ 6 min, cached in `rev_iq_bootstrap.json`) | `results/tables/rev_*.{tex,json}`, `paper/figures/rev_*.pdf`, `data/processed/analysis_sample.csv` |5960The v1.0 pipeline (`scripts/run_analysis.py`, `src/`) is kept unchanged for the record; it is not used by the revised paper.61Its outputs in `results/tables/` (non-`rev_` files) and `results/figures/01–08` are the v1.0 artefacts.6263## 6. Not modified / not possible with these data6465Nightly price of stay-regime listings (no stay length or search dates); room type, host identity, amenity list, cleaning fee,66minimum stay (not scraped); seasonality and panel variation (single cross-section); census or FSA neighbourhood identifiers67(no postal code in the Airbnb file); hedonic estimates on realised bookings.6869## 7. Build7071`cd paper && make` (latexmk, pdflatex + bibtex, `aer` style): 0 errors, 0 undefined references/citations, 0 multiply-defined72labels, 0 overfull boxes > 1 pt, 0 BibTeX warnings. 39 pages (v1.0: 28). Page 1: "Working Paper No. 4", title, author,73"October 2026", "Version 1.1"; page 2: Abstract, Keywords, JEL Classification (checked with PyMuPDF). No `main_anon.tex`74exists for this paper (not yet submitted to a journal), so no anonymous PDF was produced.75