ziyuzhou02 commited on
Commit
03d9bbe
·
verified ·
1 Parent(s): a12144d

Deploy Space: update src

Browse files
Files changed (1) hide show
  1. src/utils.py +67 -45
src/utils.py CHANGED
@@ -175,6 +175,21 @@ def format_number(value):
175
  return f"{number:.2f}"
176
 
177
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
178
  def aggregate_gmean(series: pd.Series) -> float:
179
  values = pd.to_numeric(series, errors="coerce").dropna()
180
  values = values[np.isfinite(values) & (values >= 0.0)]
@@ -192,7 +207,8 @@ def format_df(df: pd.DataFrame) -> pd.DataFrame:
192
  formatted = df.copy()
193
  for col in formatted.columns:
194
  if pd.api.types.is_numeric_dtype(formatted[col]):
195
- formatted[col] = formatted[col].map(format_number)
 
196
  return formatted
197
 
198
 
@@ -419,8 +435,9 @@ def load_gift_aggregate_table(
419
  table["Coverage"] = table["coverage"].map(
420
  lambda value: "n/a" if pd.isna(value) else f"{100.0 * float(value):.2f}%"
421
  )
422
- for metric in ("MSE", "CRPS", "Rank"):
423
  table[metric] = pd.to_numeric(table[metric], errors="coerce").map(format_number)
 
424
  table = table.rename(columns={dimension: label, "model": "Model"})
425
  return table.loc[:, columns].reset_index(drop=True)
426
 
@@ -508,6 +525,7 @@ def load_live_aggregate_table(
508
  )
509
  for metric in ("MSE", "RMSE", "MAPE", "CRPS", "RTG", "Stability", "Improvement"):
510
  frame[metric] = pd.to_numeric(frame[metric], errors="coerce").map(format_number)
 
511
  else:
512
  source_columns = [
513
  "Rank",
@@ -531,7 +549,12 @@ def load_live_aggregate_table(
531
  "pairwise_matches": "Pairwise Matches",
532
  }
533
  )
534
- for metric in ("Average Rank", "Win Rate", "Elo"):
 
 
 
 
 
535
  frame[metric] = pd.to_numeric(frame[metric], errors="coerce").map(format_number)
536
  return frame.loc[:, columns].reset_index(drop=True)
537
 
@@ -549,8 +572,8 @@ def load_live_aggregate_metadata_md(root_dir: str = "results") -> str:
549
  f"**Up to now:** {metadata.get('num_models', 0)} models, "
550
  f"{metadata.get('num_datasets', 0)} datasets, and "
551
  f"{metadata.get('num_unique_releases', 0)} distinct future releases. "
552
- "MSE/RMSE/CRPS use causal context z-normalization; RTG is relative to "
553
- "24-step Seasonal-Naive. **Generated:** "
554
  f"{generated}."
555
  )
556
 
@@ -772,7 +795,7 @@ def _read_rank_history(path: Path, date_col: str) -> pd.DataFrame:
772
  return pd.DataFrame(columns=[date_col] + _RANK_COLS)
773
  for col in _RANK_COLS:
774
  if col in df.columns:
775
- df[col] = pd.to_numeric(df[col], errors="coerce").map(format_number)
776
  if date_col in df.columns:
777
  df = df.sort_values(date_col)
778
  present = [c for c in [date_col] + _RANK_COLS if c in df.columns]
@@ -1002,26 +1025,44 @@ def _today_start_utc8() -> datetime:
1002
 
1003
  def get_dataset_last_eval_time(ds_base: str, root_dir: str = "results") -> datetime | None:
1004
  latest_dt: datetime | None = None
1005
- # Scan model directories
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1006
  for model_dir in Path(root_dir).iterdir():
1007
  if not model_dir.is_dir():
1008
  continue
1009
- forecasts_dir = model_dir / "forecasts"
1010
- if not forecasts_dir.is_dir():
1011
  continue
1012
- # Find files matching the base name
1013
- for fp in forecasts_dir.glob(f"{ds_base}*.json"):
1014
- try:
1015
- # To be super fast, regex search for evaluated_at
1016
- content = fp.read_text()
1017
- match = re.search(r'"evaluated_at"\s*:\s*"([^"]+)"', content)
1018
- if match:
1019
- eval_at = match.group(1)
1020
- dt = datetime.fromisoformat(eval_at.replace("Z", "+00:00"))
1021
- if latest_dt is None or dt > latest_dt:
1022
- latest_dt = dt
1023
- except Exception:
1024
- continue
 
 
1025
  return latest_dt
1026
 
1027
 
@@ -1076,30 +1117,11 @@ def make_domain_pie_chart(root_dir: str = "results") -> object | None:
1076
  except Exception:
1077
  pass
1078
 
1079
- # Fallback to cumulative snapshots count (no today filter) if empty
1080
  if not timestamp_counts:
1081
- seen_datasets: set[str] = set()
1082
- for model_dir in sorted(Path(root_dir).iterdir()):
1083
- if not model_dir.is_dir():
1084
- continue
1085
- forecasts_dir = model_dir / "forecasts"
1086
- if not forecasts_dir.is_dir():
1087
- continue
1088
- for fp in forecasts_dir.glob("*.json"):
1089
- try:
1090
- snap = json.loads(fp.read_text())
1091
- except Exception:
1092
- continue
1093
- ds_full = snap.get("dataset", "")
1094
- ds_base = ds_full.split("/")[0]
1095
- if ds_base in seen_datasets:
1096
- continue
1097
- seen_datasets.add(ds_base)
1098
-
1099
- domain = get_domain(ds_base)
1100
- n_ts = len(snap.get("context", [])) + len(snap.get("actuals", []))
1101
- timestamp_counts[domain] = timestamp_counts.get(domain, 0) + n_ts
1102
- domain_datasets.setdefault(domain, set()).add(dataset_short_name(ds_base))
1103
 
1104
  if not timestamp_counts:
1105
  return None
 
175
  return f"{number:.2f}"
176
 
177
 
178
+ def format_rank_number(value):
179
+ """Format rank-like columns as positive integers for leaderboard display."""
180
+ if pd.isna(value):
181
+ return "n/a"
182
+ number = float(value)
183
+ if not np.isfinite(number):
184
+ return "n/a"
185
+ return str(max(1, int(round(number))))
186
+
187
+
188
+ def _is_rank_display_column(column: object) -> bool:
189
+ name = str(column)
190
+ return "Rank" in name and name != RANK_SCORE_COLUMN
191
+
192
+
193
  def aggregate_gmean(series: pd.Series) -> float:
194
  values = pd.to_numeric(series, errors="coerce").dropna()
195
  values = values[np.isfinite(values) & (values >= 0.0)]
 
207
  formatted = df.copy()
208
  for col in formatted.columns:
209
  if pd.api.types.is_numeric_dtype(formatted[col]):
210
+ formatter = format_rank_number if _is_rank_display_column(col) else format_number
211
+ formatted[col] = formatted[col].map(formatter)
212
  return formatted
213
 
214
 
 
435
  table["Coverage"] = table["coverage"].map(
436
  lambda value: "n/a" if pd.isna(value) else f"{100.0 * float(value):.2f}%"
437
  )
438
+ for metric in ("MSE", "CRPS"):
439
  table[metric] = pd.to_numeric(table[metric], errors="coerce").map(format_number)
440
+ table["Rank"] = pd.to_numeric(table["Rank"], errors="coerce").map(format_rank_number)
441
  table = table.rename(columns={dimension: label, "model": "Model"})
442
  return table.loc[:, columns].reset_index(drop=True)
443
 
 
525
  )
526
  for metric in ("MSE", "RMSE", "MAPE", "CRPS", "RTG", "Stability", "Improvement"):
527
  frame[metric] = pd.to_numeric(frame[metric], errors="coerce").map(format_number)
528
+ frame["Rank"] = pd.to_numeric(frame["Rank"], errors="coerce").map(format_rank_number)
529
  else:
530
  source_columns = [
531
  "Rank",
 
549
  "pairwise_matches": "Pairwise Matches",
550
  }
551
  )
552
+ frame["Rank"] = pd.to_numeric(frame["Rank"], errors="coerce").map(format_rank_number)
553
+ frame["Average Rank"] = pd.to_numeric(
554
+ frame["Average Rank"],
555
+ errors="coerce",
556
+ ).map(format_rank_number)
557
+ for metric in ("Win Rate", "Elo"):
558
  frame[metric] = pd.to_numeric(frame[metric], errors="coerce").map(format_number)
559
  return frame.loc[:, columns].reset_index(drop=True)
560
 
 
572
  f"**Up to now:** {metadata.get('num_models', 0)} models, "
573
  f"{metadata.get('num_datasets', 0)} datasets, and "
574
  f"{metadata.get('num_unique_releases', 0)} distinct future releases. "
575
+ "Metrics are stored without forecasts or ground truth; RTG is relative to "
576
+ "matched Seasonal-Naive MSE. **Generated:** "
577
  f"{generated}."
578
  )
579
 
 
795
  return pd.DataFrame(columns=[date_col] + _RANK_COLS)
796
  for col in _RANK_COLS:
797
  if col in df.columns:
798
+ df[col] = pd.to_numeric(df[col], errors="coerce").map(format_rank_number)
799
  if date_col in df.columns:
800
  df = df.sort_values(date_col)
801
  present = [c for c in [date_col] + _RANK_COLS if c in df.columns]
 
1025
 
1026
  def get_dataset_last_eval_time(ds_base: str, root_dir: str = "results") -> datetime | None:
1027
  latest_dt: datetime | None = None
1028
+
1029
+ history_path = Path(root_dir) / "eval_history.jsonl"
1030
+ if history_path.exists():
1031
+ try:
1032
+ with history_path.open(encoding="utf-8") as handle:
1033
+ for line in handle:
1034
+ if not line.strip():
1035
+ continue
1036
+ entry = json.loads(line)
1037
+ if _dataset_key(entry.get("dataset", "")) != _dataset_key(ds_base):
1038
+ continue
1039
+ dt = _parse_timestamp(entry.get("evaluated_at"))
1040
+ if dt is not None and (latest_dt is None or dt > latest_dt):
1041
+ latest_dt = dt
1042
+ except Exception:
1043
+ pass
1044
+
1045
  for model_dir in Path(root_dir).iterdir():
1046
  if not model_dir.is_dir():
1047
  continue
1048
+ meta_path = model_dir / "online_meta.json"
1049
+ if not meta_path.exists():
1050
  continue
1051
+ try:
1052
+ meta = json.loads(meta_path.read_text())
1053
+ except Exception:
1054
+ continue
1055
+ matched = False
1056
+ for item in meta.get("datasets", []):
1057
+ raw_name = str(item.get("dataset", ""))
1058
+ if _dataset_key(raw_name) == _dataset_key(ds_base) or ds_base.lower() in raw_name.lower():
1059
+ matched = True
1060
+ break
1061
+ if not matched:
1062
+ continue
1063
+ dt = _parse_timestamp(meta.get("evaluated_at"))
1064
+ if dt is not None and (latest_dt is None or dt > latest_dt):
1065
+ latest_dt = dt
1066
  return latest_dt
1067
 
1068
 
 
1117
  except Exception:
1118
  pass
1119
 
1120
+ # Fallback to one count per current dataset if history is unavailable.
1121
  if not timestamp_counts:
1122
+ for ds_base, domain in domain_map.items():
1123
+ timestamp_counts[domain] = timestamp_counts.get(domain, 0) + 1
1124
+ domain_datasets.setdefault(domain, set()).add(dataset_short_name(ds_base))
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1125
 
1126
  if not timestamp_counts:
1127
  return None