| import json |
|
|
| import gradio as gr |
| import numpy as np |
| from fastchrf import aggregate_chrf, pairwise_chrf |
|
|
|
|
| def parse_lines(text: str) -> list[str]: |
| lines = [line.strip() for line in text.splitlines() if line.strip()] |
| if not lines: |
| raise gr.Error("Provide at least one non-empty line.") |
| return lines |
|
|
|
|
| def compute_chrf( |
| mode: str, |
| hypotheses_text: str, |
| references_text: str, |
| char_order: int, |
| beta: float, |
| remove_whitespace: bool, |
| eps_smoothing: bool, |
| ) -> str: |
| hypotheses = parse_lines(hypotheses_text) |
| references = parse_lines(references_text) |
|
|
| if mode == "default": |
| scores = pairwise_chrf( |
| [hypotheses], |
| [references], |
| char_order=char_order, |
| beta=beta, |
| remove_whitespace=remove_whitespace, |
| eps_smoothing=eps_smoothing, |
| ) |
| array = np.array(scores[0]) |
| payload = { |
| "mode": "default", |
| "shape": list(array.shape), |
| "scores": array.tolist(), |
| "hypotheses": hypotheses, |
| "references": references, |
| } |
| else: |
| scores = aggregate_chrf( |
| [hypotheses], |
| [references], |
| char_order=char_order, |
| beta=beta, |
| remove_whitespace=remove_whitespace, |
| eps_smoothing=eps_smoothing, |
| ) |
| array = np.array(scores[0]) |
| payload = { |
| "mode": "aggregate", |
| "shape": list(array.shape), |
| "scores": array.tolist(), |
| "hypotheses": hypotheses, |
| "references": references, |
| } |
|
|
| return json.dumps(payload, indent=2, ensure_ascii=False) |
|
|
|
|
| EXAMPLE_HYPOTHESES = """The cat sat on the mat. |
| The cat sat on the hat.""" |
|
|
| EXAMPLE_REFERENCES = """The cat sat on the mat. |
| The fat cat sat on the mat. |
| A cat sat on a mat.""" |
|
|
| with gr.Blocks(title="fastChrF") as demo: |
| gr.Markdown( |
| """ |
| # fastChrF |
| |
| Fast sentence-level ChrF for Minimum Bayes Risk decoding. |
| |
| - **Default (pairwise):** ChrF between each hypothesis and each reference. |
| - **Aggregate:** Streamlined variant that aggregates across references. |
| |
| [GitHub](https://github.com/jvamvas/fastChrF) · [Paper](https://arxiv.org/abs/2402.04251) |
| """ |
| ) |
|
|
| with gr.Row(): |
| mode = gr.Radio( |
| choices=["default", "aggregate"], |
| value="default", |
| label="Mode", |
| info="Default (pairwise) returns a hypothesis × reference matrix; aggregate returns one score per hypothesis.", |
| ) |
|
|
| with gr.Row(): |
| hypotheses = gr.Textbox( |
| label="Hypotheses (one per line)", |
| lines=8, |
| placeholder="Enter one hypothesis per line", |
| value=EXAMPLE_HYPOTHESES, |
| ) |
| references = gr.Textbox( |
| label="References (one per line)", |
| lines=8, |
| placeholder="Enter one reference per line", |
| value=EXAMPLE_REFERENCES, |
| ) |
|
|
| with gr.Accordion("Advanced options", open=False): |
| with gr.Row(): |
| char_order = gr.Slider( |
| minimum=1, |
| maximum=10, |
| value=6, |
| step=1, |
| label="Character n-gram order", |
| ) |
| beta = gr.Slider( |
| minimum=0.1, |
| maximum=5.0, |
| value=2.0, |
| step=0.1, |
| label="Beta (F-score weight)", |
| ) |
| with gr.Row(): |
| remove_whitespace = gr.Checkbox(value=True, label="Remove whitespace") |
| eps_smoothing = gr.Checkbox(value=False, label="Epsilon smoothing") |
|
|
| compute_button = gr.Button("Compute ChrF", variant="primary") |
| output = gr.Code(label="Results (JSON)", language="json", lines=20) |
|
|
| compute_button.click( |
| fn=compute_chrf, |
| inputs=[ |
| mode, |
| hypotheses, |
| references, |
| char_order, |
| beta, |
| remove_whitespace, |
| eps_smoothing, |
| ], |
| outputs=output, |
| ) |
|
|
| gr.Examples( |
| examples=[ |
| [EXAMPLE_HYPOTHESES, EXAMPLE_REFERENCES, "default"], |
| [EXAMPLE_HYPOTHESES, EXAMPLE_REFERENCES, "aggregate"], |
| ], |
| inputs=[hypotheses, references, mode], |
| label="Examples", |
| ) |
|
|
| if __name__ == "__main__": |
| demo.launch() |
|
|