Download services/scoring/scoring_function.py from silvanus0930/vidaio-subnet: direct link, hf CLI and curl.
- Browser
- Download file 12.2 kB
-
https://huggingface.co/silvanus0930/vidaio-subnet/resolve/main/services/scoring/scoring_function.py
- Command line
-
hf download hf://silvanus0930/vidaio-subnet/services/scoring/scoring_function.py
-
curl -L -o scoring_function.py https://huggingface.co/silvanus0930/vidaio-subnet/resolve/main/services/scoring/scoring_function.py
12.2 kB
| import math | |
| def calculate_compression_score( | |
| vmaf_score: float, | |
| compression_rate: float, | |
| vmaf_threshold: float, | |
| compression_weight: float = 0.70, | |
| quality_weight: float = 0.30, | |
| soft_threshold_margin: float = 5.0) -> tuple[float, float, float, str]: | |
| """ | |
| Calculate compression score that rewards hitting VMAF threshold with good compression. | |
| Scoring Philosophy: | |
| - Compression is primary goal (70% weight by default) | |
| - VMAF at/above threshold is rewarded with diminishing returns (30% weight) | |
| - 20x compression ratio = 1.0 compression component | |
| - Exceeding VMAF threshold gives modest bonus (not penalty) | |
| Three scoring zones: | |
| 1. Below hard cutoff (threshold - 5): Score = 0 | |
| 2. Soft zone (threshold - 5 to threshold): Gradual recovery | |
| 3. Above threshold: Full scoring with quality bonus | |
| Args: | |
| vmaf_score: VMAF quality score (0-100) | |
| compression_rate: Size ratio compressed/original (0-1, lower is better) | |
| vmaf_threshold: Required VMAF threshold (e.g., 85, 89, 93) | |
| compression_weight: Weight for compression component (default: 0.70) | |
| quality_weight: Weight for quality component (default: 0.30) | |
| soft_threshold_margin: Points below threshold before hard cutoff (default: 5.0) | |
| Returns: | |
| Tuple of (final_score, compression_component, quality_component, reason) | |
| where final_score is in range [0.0, 1.0] | |
| """ | |
| # Validate that weights sum to 1.0 | |
| if abs(compression_weight + quality_weight - 1.0) > 0.01: | |
| raise ValueError(f"Weights must sum to 1.0, got {compression_weight + quality_weight}") | |
| # Calculate hard cutoff point | |
| hard_cutoff = vmaf_threshold - soft_threshold_margin | |
| # ======================================================================== | |
| # CASE 0: No Meaningful Compression - Immediate Failure | |
| # ======================================================================== | |
| # If compression_rate >= 0.80 (less than 1.25x compression), this is likely | |
| # the miner returning the same video or minimal compression to exploit high VMAF. | |
| # Zero the entire score to prevent this exploit. | |
| if compression_rate >= 0.80: | |
| compression_ratio = 1 / compression_rate if compression_rate > 0 else 1.0 | |
| return 0.0, 0.0, 0.0, f"No meaningful compression (ratio: {compression_ratio:.2f}x, rate: {compression_rate:.2f}). Minimum 1.25x required." | |
| # ======================================================================== | |
| # CASE 1: Below Hard Cutoff - Immediate Failure | |
| # ======================================================================== | |
| # If VMAF is more than 5 points below threshold, quality is unacceptable | |
| if vmaf_score < hard_cutoff: | |
| return 0.0, 0.0, 0.0, f"VMAF {vmaf_score:.2f} below hard cutoff ({hard_cutoff:.2f})" | |
| # ======================================================================== | |
| # CASE 2: Soft Threshold Zone (threshold-5 to threshold) | |
| # ======================================================================== | |
| # Gradual recovery zone where both quality and compression matter | |
| if vmaf_score < vmaf_threshold: | |
| # Calculate position in soft zone (0.0 to 1.0) | |
| # Example: VMAF 93 with threshold 95 and margin 5 | |
| # soft_zone_position = (93 - 90) / 5 = 0.6 | |
| soft_zone_position = (vmaf_score - hard_cutoff) / soft_threshold_margin | |
| """ | |
| Quality factor uses scaled function to reach 0.7 at threshold: | |
| f(x) = 0.7 * x² | |
| - At hard cutoff (x=0): factor = 0.0 | |
| - At midpoint (x=0.5): factor = 0.175 | |
| - At threshold (x=1): factor = 0.7 | |
| This ensures continuity with the above-threshold quality component | |
| which starts at 0.7 when VMAF equals threshold. | |
| """ | |
| quality_factor = 0.7 * (soft_zone_position ** 2) | |
| # Calculate compression component (compression_rate < 0.80 guaranteed by CASE 0) | |
| compression_ratio = 1 / compression_rate | |
| if compression_ratio <= 20: | |
| """ | |
| Compression scoring for 1x to 20x: | |
| f(r) = ((r - 1) / 19) ^ 1.5 | |
| Where r is compression ratio (e.g., 5 for 5x compression) | |
| - At 1x: component = 0 | |
| - At 2x: component ≈ 0.23 | |
| - At 5x: component ≈ 0.65 | |
| - At 10x: component ≈ 0.89 | |
| - At 15x: component ≈ 0.97 | |
| - At 20x: component = 1.0 | |
| The exponent 1.5 provides: | |
| - Slow growth initially (encouraging minimum viable compression) | |
| - Steeper growth in practical range (5-15x) | |
| - Reaches 1.0 exactly at 20x | |
| """ | |
| compression_component = ((compression_ratio - 1) / 19) ** 1.5 | |
| else: | |
| """ | |
| Bonus for exceptional compression (>20x): | |
| f(r) = 1.0 + 0.3 * ln(r / 20) | |
| Logarithmic bonus rewards exceptional performance: | |
| - At 20x: component = 1.0 (continuous at boundary) | |
| - At 30x: component ≈ 1.12 | |
| - At 40x: component ≈ 1.21 | |
| - At 60x: component ≈ 1.30 (capped) | |
| Natural log ensures smooth transition from linear region. | |
| """ | |
| compression_component = 1.0 + 0.3 * math.log(compression_ratio / 20) | |
| # compression_component = min(1.3, compression_component) | |
| # In soft zone, both compression AND quality factor matter | |
| # If you're below threshold, you need good compression to recover | |
| # Normalization factor based on max theoretical score at 100x compression | |
| normalization_factor = 1.12 | |
| final_score = (compression_component * quality_factor) / normalization_factor | |
| return min(1.0, final_score), compression_component, quality_factor, f"VMAF {vmaf_score:.2f} in soft zone (quality factor: {quality_factor:.2f})" | |
| # ======================================================================== | |
| # CASE 3: Above Threshold - Full Scoring with Quality Bonus | |
| # ======================================================================== | |
| else: | |
| # Calculate how much VMAF exceeds threshold | |
| vmaf_excess = vmaf_score - vmaf_threshold | |
| max_vmaf_excess = 100 - vmaf_threshold # Maximum possible excess to VMAF 100 | |
| """ | |
| Quality component rewards exceeding threshold with linear interpolation: | |
| f(x) = 0.7 + 0.3 * (x / max_excess) | |
| Where x is VMAF points above threshold: | |
| - At threshold (x=0): component = 0.7 | |
| - At threshold + 25% of range: component = 0.775 | |
| - At threshold + 50% of range: component = 0.85 | |
| - At threshold + 75% of range: component = 0.925 | |
| - At VMAF 100: component = 1.0 | |
| Example with threshold=85: | |
| - At 85: 0.7 + 0.3 * (0/15) = 0.7 | |
| - At 90: 0.7 + 0.3 * (5/15) = 0.8 | |
| - At 95: 0.7 + 0.3 * (10/15) = 0.9 | |
| - At 100: 0.7 + 0.3 * (15/15) = 1.0 | |
| This provides steady linear growth from 0.7 to 1.0 as VMAF approaches perfect quality. | |
| """ | |
| quality_component = ( | |
| 1.0 | |
| if max_vmaf_excess <= 0 | |
| else 0.7 + 0.3 * min(1.0, vmaf_excess / max_vmaf_excess) | |
| ) | |
| # Calculate compression component (compression_rate < 0.80 guaranteed by CASE 0) | |
| compression_ratio = 1 / compression_rate | |
| if compression_ratio <= 20: | |
| """ | |
| Good compression scoring (1.25x to 20x): | |
| f(r) = ((r - 1.25) / 18.75) ^ 0.9 | |
| Starting from 1.25x to give smooth transition from poor zone: | |
| - At 1.25x: component = ((1.25 - 1.25) / 18.75) ^ 0.9 = 0.0 | |
| - At 2x: component = ((2 - 1.25) / 18.75) ^ 0.9 = 0.04 ^ 0.9 = 0.055 | |
| - At 5x: component = ((5 - 1.25) / 18.75) ^ 0.9 = 0.235 | |
| - At 10x: component = ((10 - 1.25) / 18.75) ^ 0.9 = 0.504 | |
| - At 15x: component = ((15 - 1.25) / 18.75) ^ 0.9 = 0.756 | |
| - At 20x: component = ((20 - 1.25) / 18.75) ^ 0.9 = 1.0 | |
| """ | |
| compression_component = ((compression_ratio - 1.25) / 18.75) ** 0.9 | |
| else: | |
| """ | |
| Exceptional compression bonus (>20x): | |
| f(r) = 1.0 + 0.1 * ln(r / 20) | |
| Logarithmic bonus: | |
| - At 20x: component = 1.0 | |
| - At 50x: component ≈ 1.09 | |
| - At 100x: component ≈ 1.16 | |
| Reduced multiplier compresses the dynamic range. | |
| """ | |
| compression_component = 1.0 + 0.1 * math.log(compression_ratio / 20) | |
| # compression_component = min(1.3, compression_component) | |
| reason_suffix = "" if compression_ratio < 10 else " (excellent compression)" | |
| """ | |
| Final score is weighted combination: | |
| final_score = w_c * compression_component + w_q * quality_component | |
| Default: 70% compression + 30% quality | |
| Capped at 1.0 to maintain normalized scoring | |
| """ | |
| # Normalization factor based on max theoretical score at 100x compression | |
| normalization_factor = 1.12 | |
| final_score = (compression_weight * compression_component + | |
| quality_weight * quality_component) / normalization_factor | |
| final_score = min(1.0, final_score) | |
| return final_score, compression_component, quality_component, f"success{reason_suffix}" | |
| if __name__ == "__main__": | |
| import numpy as np | |
| import matplotlib.pyplot as plt | |
| from mpl_toolkits.mplot3d import Axes3D # noqa: F401 | |
| # --- Configuration --- | |
| vmaf_thresholds = [85, 89, 93] | |
| vmaf_values = np.linspace(75, 100, 200) | |
| compression_ratios = np.linspace(1.0, 100.0, 200) # 1x to 100x | |
| fig, axes = plt.subplots( | |
| 2, len(vmaf_thresholds), | |
| figsize=(6 * len(vmaf_thresholds), 11), | |
| gridspec_kw={"height_ratios": [1, 1.2]}, | |
| ) | |
| for col, threshold in enumerate(vmaf_thresholds): | |
| # Build score grid (VMAF on Y, compression ratio on X) | |
| scores = np.zeros((len(vmaf_values), len(compression_ratios))) | |
| for i, vmaf in enumerate(vmaf_values): | |
| for j, cr in enumerate(compression_ratios): | |
| rate = 1.0 / cr # compression_rate = 1 / ratio | |
| final_score, *_ = calculate_compression_score( | |
| vmaf_score=vmaf, | |
| compression_rate=rate, | |
| vmaf_threshold=threshold, | |
| ) | |
| scores[i, j] = final_score | |
| # ---- Row 0: Heatmap ---- | |
| ax_heat = axes[0, col] | |
| cr_extent = [compression_ratios[0], compression_ratios[-1]] | |
| vmaf_extent = [vmaf_values[0], vmaf_values[-1]] | |
| im = ax_heat.imshow( | |
| scores, | |
| aspect="auto", | |
| origin="lower", | |
| extent=cr_extent + vmaf_extent, | |
| cmap="viridis", | |
| # vmin=0, | |
| # vmax=1, | |
| ) | |
| ax_heat.set_xlabel("Compression Ratio (x)") | |
| ax_heat.set_ylabel("VMAF Score") | |
| ax_heat.set_title(f"Threshold = {threshold}") | |
| fig.colorbar(im, ax=ax_heat, label="Final Score") | |
| # ---- Row 1: 3D Surface ---- | |
| ax_3d = fig.add_subplot(2, len(vmaf_thresholds), len(vmaf_thresholds) + col + 1, projection="3d") | |
| axes[1, col].set_visible(False) # hide the flat axes placeholder | |
| CR, VMAF = np.meshgrid(compression_ratios, vmaf_values) | |
| ax_3d.plot_surface(CR, VMAF, scores, cmap="viridis", edgecolor="none", alpha=0.9) | |
| ax_3d.set_xlabel("Comp. Ratio (x)") | |
| ax_3d.set_ylabel("VMAF") | |
| ax_3d.set_zlabel("Score") | |
| ax_3d.set_title(f"Threshold = {threshold}") | |
| ax_3d.view_init(elev=30, azim=-135) | |
| fig.suptitle("Final Score vs VMAF & Compression Ratio", fontsize=15, y=0.98) | |
| plt.tight_layout(rect=[0, 0, 1, 0.96]) | |
| import os | |
| out_path = os.path.join(os.path.dirname(os.path.abspath(__file__)), "scoring_plot.png") | |
| plt.savefig(out_path, dpi=200, bbox_inches="tight") | |
| print(f"Plot saved to {out_path}") | |