File size: 7,027 Bytes
68d6f94 6d56e7f 68d6f94 6d56e7f 68d6f94 6d56e7f 68d6f94 6d56e7f 68d6f94 6d56e7f |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 |
import gradio as gr
import pandas as pd
from datasets import load_dataset
from deep_translator import GoogleTranslator
from huggingface_hub import login
import os
# --- 定数と初期設定 ---
# Hugging Faceトークンを環境変数から取得
HF_TOKEN = os.environ.get("HF_TOKEN")
# --- グローバル変数 ---
# データは一度だけロードする
dataset = None
df = None
category_counts = None
# --- データ処理関数 ---
def load_and_process_data():
"""データセットをロードし、グローバル変数を初期化する"""
global dataset, df, category_counts
if dataset is not None:
return
try:
# トークンがあればログイン
if HF_TOKEN:
login(token=HF_TOKEN)
dataset = load_dataset("cais/hle", split="test")
# 画像データを扱うため、Pandasに変換するのはメタデータのみ
df = dataset.remove_columns(['image_preview', 'rationale_image']).to_pandas()
category_counts = df['category'].value_counts()
print("データセットのロードと前処理が完了しました。")
except Exception as e:
print(f"データセットのロードエラー: {e}")
# エラーが発生した場合、アプリがクラッシュしないように空のデータフレームを設定
df = pd.DataFrame(columns=['id', 'question', 'category'])
category_counts = pd.Series()
# --- 翻訳関数 ---
def translate_text(text, dest_lang='ja'):
"""テキストを翻訳します"""
if not text or not isinstance(text, str):
return ""
try:
# GoogleTranslatorを使用(deep-translator)
translator = GoogleTranslator(source='auto', target=dest_lang)
return translator.translate(text)
except Exception as e:
print(f"翻訳エラー: {e}")
return f"翻訳エラー: {str(e)}"
# --- Gradioイベントハンドラ ---
def on_category_change(selected_category):
"""カテゴリが変更されたときに、問題のドロップダウンを更新する"""
if selected_category == "全カテゴリ":
filtered_indices = df.index
else:
filtered_indices = df[df['category'] == selected_category].index
# 選択肢を (表示名, 値) のタプル形式で作成
question_choices = [
(f"{df.loc[idx, 'question'][:80]}...", idx) for idx in filtered_indices
]
if not question_choices:
# 選択肢がない場合は、表示をクリアし、選択不可にする
return gr.Dropdown(choices=[], label="問題 (該当なし)", interactive=False, value=None)
else:
return gr.Dropdown(choices=question_choices, label="問題を選択", interactive=True, value=question_choices[0][1])
def on_question_change(selected_index):
"""問題が選択されたときに、すべての詳細表示を更新する"""
if selected_index is None or pd.isna(selected_index):
# 空の出力をまとめて返す
empty_outputs = [gr.Markdown(visible=False)] * 6 + [gr.Image(visible=False)] * 2
return tuple(empty_outputs)
# 元のHugging Face Datasetから完全なエントリを取得
entry = dataset[int(selected_index)]
# 各要素の翻訳
q_trans = translate_text(entry['question'])
a_trans = translate_text(entry['answer'])
r_trans = translate_text(entry.get('rationale', ''))
# 出力コンポーネントの値を生成
outputs = {
"question_md": gr.Markdown(f"### 質問\n---\n**原文:**\n{entry['question']}\n\n**日本語訳:**\n{q_trans}", visible=True),
"question_img": gr.Image(entry.get('image_preview'), label="質問画像", visible=bool(entry.get('image_preview'))),
"answer_md": gr.Markdown(f"### 回答\n---\n**原文:**\n{entry['answer']}\n\n**日本語訳:**\n{a_trans}", visible=True),
"rationale_md": gr.Markdown(f"### 解説\n---\n**原文:**\n{entry.get('rationale', 'N/A')}\n\n**日本語訳:**\n{r_trans}", visible=bool(entry.get('rationale'))),
"rationale_img": gr.Image(entry.get('rationale_image'), label="解説画像", visible=bool(entry.get('rationale_image'))),
"metadata_md": gr.Markdown(f"**ID:** `{entry['id']}`<br>**分野:** `{entry['raw_subject']}`<br>**回答タイプ:** `{entry['answer_type']}`", visible=True),
"json_output": gr.JSON({k: str(v) for k, v in entry.items()}, label="元のデータ", visible=True)
}
# 定義された順序で値を返す
return (
outputs["question_md"],
outputs["question_img"],
outputs["answer_md"],
outputs["rationale_md"],
outputs["rationale_img"],
outputs["metadata_md"],
outputs["json_output"]
)
# --- Gradio UI構築 ---
def create_demo():
# アプリケーション起動時に一度だけデータをロード
load_and_process_data()
with gr.Blocks(theme=gr.themes.Soft(), title="HLE Dataset Viewer") as demo:
gr.Markdown("# Humanity's Last Exam (HLE) Dataset Viewer")
gr.Markdown("Hugging Face `cais/hle`データセットを探索し、日本語訳を確認できます。")
with gr.Row():
with gr.Column(scale=1, min_width=350):
gr.Markdown("## 操作パネル")
category_dd = gr.Dropdown(
choices=["全カテゴリ"] + sorted(category_counts.index.tolist()),
value="全カテゴリ",
label="1. カテゴリを選択"
)
question_dd = gr.Dropdown(label="2. 問題を選択", interactive=False)
gr.Markdown("### カテゴリ別問題数")
gr.Dataframe(value=pd.DataFrame(category_counts).reset_index(), headers=['カテゴリ', '問題数'], interactive=False)
with gr.Column(scale=3):
# 出力エリアのプレースホルダー
metadata_md = gr.Markdown(visible=False)
question_md = gr.Markdown(visible=False)
question_img = gr.Image(label="質問画像", visible=False)
answer_md = gr.Markdown(visible=False)
rationale_md = gr.Markdown(visible=False)
rationale_img = gr.Image(label="解説画像", visible=False)
json_output = gr.JSON(label="元のデータ", visible=False)
# イベントリスナーを設定
category_dd.change(fn=on_category_change, inputs=category_dd, outputs=question_dd)
question_dd.change(fn=on_question_change, inputs=question_dd, outputs=[
question_md, question_img, answer_md, rationale_md, rationale_img, metadata_md, json_output
])
# 初期表示のために最初のカテゴリ変更イベントをトリガー
demo.load(fn=on_category_change, inputs=category_dd, outputs=question_dd)
return demo
# --- アプリケーション起動 ---
if __name__ == "__main__":
app = create_demo()
app.launch() |