Application1 / app.py
fusin001's picture
Upload folder using huggingface_hub
3287c72 verified
Raw
History Blame Contribute Delete
4.22 kB
import gradio as gr
import pandas as pd
import numpy as np
import pickle
import os
# Load model
model_filename = "apartment_rf_model.pkl"
with open(model_filename, mode="rb") as f:
model_data = pickle.load(f)
model = model_data["model"]
features = model_data["features"]
log_target = model_data["log_target"]
DEFAULT_POP_DENS_CITY = 4729.0
DEFAULT_POP_DENS_OUTSIDE = 1328.0
DEFAULT_FRG_PCT = 25.0
DEFAULT_LAT_CITY = 47.380402
DEFAULT_LON_CITY = 8.530496
DEFAULT_LAT_OUTSIDE = 47.424900
DEFAULT_LON_OUTSIDE = 8.638663
def predict_price(
rooms, area, tax_income,
luxurious, furnished, temporary, zurich_city,
attika, loft, seesicht,
kreis
):
# Use data-derived defaults for hidden features
pop_dens = DEFAULT_POP_DENS_CITY if zurich_city else DEFAULT_POP_DENS_OUTSIDE
lat = DEFAULT_LAT_CITY if zurich_city else DEFAULT_LAT_OUTSIDE
lon = DEFAULT_LON_CITY if zurich_city else DEFAULT_LON_OUTSIDE
frg_pct = DEFAULT_FRG_PCT
# Derived features
log_area = np.log1p(area)
log_rooms = np.log1p(rooms)
rooms_area_ratio = rooms / (area + 1)
room_per_m2 = area / rooms if rooms > 0 else area
income_density_score = tax_income * pop_dens / 1e6
log_income_dens = np.log1p(income_density_score)
log_pop_dens = np.log1p(pop_dens)
area_rooms_interact = area * rooms
# Kreis dummies
kreis_cols = {f"Kreis {i}": 0 for i in range(1, 13)}
if kreis in kreis_cols:
kreis_cols[kreis] = 1
input_dict = {
"rooms": rooms,
"area": area,
"log_area": log_area,
"log_rooms": log_rooms,
"pop_dens": pop_dens,
"log_pop_dens": log_pop_dens,
"frg_pct": frg_pct,
"tax_income": tax_income,
"income_density_score": income_density_score,
"log_income_dens": log_income_dens,
"rooms_area_ratio": rooms_area_ratio,
"area_rooms_interact": area_rooms_interact,
"lat": lat,
"lon": lon,
"luxurious": int(luxurious),
"furnished": int(furnished),
"temporary": int(temporary),
"zurich_city": int(zurich_city),
"room_per_m2": room_per_m2,
**kreis_cols,
"(ATTIKA)": int(attika),
"(LOFT)": int(loft),
"(SEESICHT)": int(seesicht),
"(LUXURIÖS)": 0,
"(POOL)": 0,
"(EXKLUSIV)": 0,
}
input_df = pd.DataFrame([input_dict])[features]
prediction_log = model.predict(input_df)[0]
prediction = np.expm1(prediction_log)
return f"Estimated Monthly Rent: **CHF {prediction:,.0f}**"
demo = gr.Interface(
fn=predict_price,
inputs=[
gr.Number(label="Number of Rooms", value=3.0),
gr.Number(label="Living Area (m²)", value=80),
gr.Number(label="Municipal Tax Income (CHF)", value=80000),
gr.Checkbox(label="Luxurious"),
gr.Checkbox(label="Furnished"),
gr.Checkbox(label="Temporary"),
gr.Checkbox(label="Located in Zurich City"),
gr.Checkbox(label="Attika (Penthouse)"),
gr.Checkbox(label="Loft"),
gr.Checkbox(label="Lake View (Seesicht)"),
gr.Dropdown(
label="Zurich District (Kreis)",
choices=["None"] + [f"Kreis {i}" for i in range(1, 13)],
value="None"
),
],
outputs=gr.Markdown(),
submit_btn="Predict Rent",
examples=[
[3.0, 80, 70000, False, False, False, True, False, False, False, "Kreis 3"],
[4.5, 120, 120000, True, False, False, True, True, False, True, "Kreis 1"],
[2.0, 55, 55000, False, True, False, False, False, False, False, "None"],
],
title="Zurich Apartment Rent Predictor",
description=(
"Predict the monthly rental price for an apartment in the Canton of Zurich.\n\n"
"This model uses a **Gradient Boosting Regressor** trained on ~800 Zurich apartment listings, "
"with features including location (district), apartment characteristics, "
"and the **Income-Density Score** (a neighbourhood affluence proxy)."
),
theme=gr.themes.Soft(),
)
if __name__ == "__main__":
demo.launch()