Buckets:
| # Implementarea GRPO în TRL | |
| În această pagină, vom învăța cum să implementăm Optimizarea Relativă a Politicii de Grup (GRPO) folosind biblioteca Transformer Reinforcement Learning (TRL). Ne vom concentra pe implementarea practică cu cod minimal. | |
| Vom explora conceptele centrale ale GRPO așa cum sunt întruchipate în GRPOTrainer din TRL, folosind fragmente din documentația oficială TRL pentru a ne ghida. | |
| > [!TIP] | |
| > Acest capitol este destinat începătorilor TRL. Dacă ești deja familiar cu TRL, ai putea de asemenea să consulți [implementarea Open R1](https://github.com/huggingface/open-r1/blob/main/src/open_r1/grpo.py) a GRPO. | |
| În primul rând, să ne reamintim unele dintre conceptele importante ale algoritmului GRPO: | |
| - Formarea Grupului: Modelul generează multiple completări pentru fiecare prompt. | |
| - Învățarea Preferințelor: Modelul învață dintr-o funcție de recompensă care compară grupuri de completări. | |
| - Configurația Antrenamentului: Modelul folosește o configurație pentru a controla procesul de antrenare. | |
| Ce trebuie să facem pentru a implementa GRPO? | |
| - Să definim un set de date de prompt-uri. | |
| - Să definim o funcție de recompensă care ia o listă de completări și returnează o listă de recompense. | |
| - Să configurăm procesul de antrenare cu un GRPOConfig. | |
| - Să antrenăm modelul folosind GRPOTrainer. | |
| Iată un exemplu minimal pentru a începe antrenamentul GRPO: | |
| ```python | |
| from trl import GRPOTrainer, GRPOConfig | |
| from datasets import load_dataset | |
| # 1. Încarcă setul tău de date | |
| dataset = load_dataset("setul_tau_de_date", split="train") | |
| # 2. Definește o funcție de recompensă simplă | |
| def reward_func(completions, **kwargs): | |
| """Exemplu: Recompensează completările mai lungi""" | |
| return [float(len(completion)) for completion in completions] | |
| # 3. Configurează antrenamentul | |
| training_args = GRPOConfig( | |
| output_dir="output", | |
| num_train_epochs=3, | |
| per_device_train_batch_size=4, | |
| gradient_accumulation_steps=2, | |
| logging_steps=10, | |
| ) | |
| # 4. Inițializează și antrenează | |
| trainer = GRPOTrainer( | |
| model="modelul_tau", # de exemplu "Qwen/Qwen2-0.5B-Instruct" | |
| args=training_args, | |
| train_dataset=dataset, | |
| reward_funcs=reward_func, | |
| ) | |
| trainer.train() | |
| ``` | |
| ## Componentele Cheie | |
| ### 1. Formatul Setului de Date | |
| Setul tău de date ar trebui să conțină prompt-uri la care modelul va răspunde. Antrenorul GRPO va genera multiple completări pentru fiecare prompt și va folosi funcția de recompensă pentru a le compara. | |
| ### 2. Funcția de Recompensă | |
| Funcția de recompensă este crucială - determină cum învață modelul. Iată două exemple practice: | |
| ```python | |
| # Exemplul 1: Recompensă bazată pe lungimea completării | |
| def reward_length(completions, **kwargs): | |
| return [float(len(completion)) for completion in completions] | |
| # Exemplul 2: Recompensă bazată pe potrivirea unui model | |
| import re | |
| def reward_format(completions, **kwargs): | |
| pattern = r"^<think>.*?</think><answer>.*?</answer>$" | |
| return [1.0 if re.match(pattern, c) else 0.0 for c in completions] | |
| ``` | |
| ### 3. Configurația Antrenamentului | |
| Parametrii cheie de considerat în `GRPOConfig`: | |
| ```python | |
| training_args = GRPOConfig( | |
| # Parametrii esențiali | |
| output_dir="output", | |
| num_train_epochs=3, | |
| num_generation=4, # Numărul de completări de generat pentru fiecare prompt | |
| per_device_train_batch_size=4, # Vrem să obținem toate generările într-un lot de dispozitiv | |
| # Opțional dar util | |
| gradient_accumulation_steps=2, | |
| learning_rate=1e-5, | |
| logging_steps=10, | |
| # Specific GRPO (opțional) | |
| use_vllm=True, # Accelerează generarea | |
| ) | |
| ``` | |
| Parametrul `num_generation` este deosebit de important pentru GRPO deoarece definește dimensiunea grupului - câte completări diferite va genera modelul pentru fiecare prompt. Acesta este un diferențiator cheie de alte metode RL: | |
| - Prea mic (de exemplu, 2-3): S-ar putea să nu ofere suficientă diversitate pentru comparații semnificative | |
| - Recomandat (4-16): Oferă un echilibru bun între diversitate și eficiența computațională | |
| - Valori mai mari: Pot îmbunătăți învățarea dar cresc semnificativ costul computațional | |
| Dimensiunea grupului ar trebui aleasă în funcție de resursele tale computaționale și complexitatea sarcinii tale. Pentru sarcini simple, grupuri mai mici (4-8) pot fi suficiente, în timp ce sarcinile de raționament mai complexe ar putea beneficia de grupuri mai mari (8-16). | |
| ## Sfaturi pentru Succes | |
| 1. **Gestionarea Memoriei**: Ajustează `per_device_train_batch_size` și `gradient_accumulation_steps` în funcție de memoria GPU-ului tău. | |
| 2. **Viteza**: Activează `use_vllm=True` pentru generare mai rapidă dacă modelul tău este suportat. | |
| 3. **Monitorizarea**: Urmărește metricile înregistrate în timpul antrenamentului: | |
| - `reward`: Recompensa medie pe completări | |
| - `reward_std`: Deviația standard în cadrul grupurilor de recompense | |
| - `kl`: Divergența KL de la modelul de referință | |
| ## Designul Funcției de Recompensă | |
| Lucrarea DeepSeek R1 demonstrează mai multe abordări eficiente pentru designul funcției de recompensă pe care le poți adapta pentru propria ta implementare GRPO: | |
| ### 1. Recompense Bazate pe Lungime | |
| Una dintre cele mai ușoare recompense de implementat este o recompensă bazată pe lungime. Poți recompensa completări mai lungi: | |
| ```python | |
| def reward_len(completions, **kwargs): | |
| ideal_length = 20 | |
| return [-abs(ideal_length - len(completion)) for completion in completions] | |
| ``` | |
| Această funcție de recompensă penalizează completările care sunt prea scurte sau prea lungi, încurajând modelul să genereze completări care sunt aproape de lungimea ideală de 20 de token-uri. | |
| <!-- # TODO: update links when PR is merged --> | |
| <iframe | |
| src="https://marimo.app/gh/huggingface/notebooks/main/e?entrypoint=course%2Fen%2Fchapter13%2Fgrpo_length.py&embed=true&show-chrome=false" | |
| title="Marimo Notebook" | |
| width="100%" | |
| height="800px" | |
| frameBorder="0" | |
| allow="clipboard-write" | |
| ></iframe> | |
| ## 2. Recompense Bazate pe Reguli pentru Sarcini Verificabile | |
| Pentru sarcini cu răspunsuri obiectiv corecte (cum ar fi matematica sau codarea), poți implementa funcții de recompensă bazate pe reguli: | |
| ```python | |
| def problem_reward(completions, answers, **kwargs): | |
| """Funcție de recompensă pentru probleme de matematică cu răspunsuri verificabile | |
| completions: lista de completări de evaluat | |
| answers: lista de răspunsuri la problemele din setul de date | |
| """ | |
| rewards = [] | |
| for completion, correct_answer in zip(completions, answers): | |
| # Extrage răspunsul din completare | |
| try: | |
| # Acesta este un exemplu simplificat - ai avea nevoie de parsing corespunzător | |
| answer = extract_final_answer(completion) | |
| # Recompensă binară: 1 pentru corect, 0 pentru incorect | |
| reward = 1.0 if answer == correct_answer else 0.0 | |
| rewards.append(reward) | |
| except: | |
| # Dacă nu putem parsa un răspuns, dăm o recompensă mică | |
| rewards.append(0.0) | |
| return rewards | |
| ``` | |
| <!-- # TODO: update links when PR is merged --> | |
| <iframe | |
| src="https://marimo.app/gh/huggingface/notebooks/main/e?entrypoint=course%2Fen%2Fchapter13%2Fgrpo_math.py&embed=true&show-chrome=false" | |
| title="Marimo Notebook" | |
| width="100%" | |
| height="800px" | |
| frameBorder="0" | |
| allow="clipboard-write" | |
| ></iframe> | |
| ## 3. Recompense Bazate pe Format | |
| Poți de asemenea să recompensezi formatarea corespunzătoare, care a fost importantă în antrenamentul DeepSeek R1: | |
| ```python | |
| def format_reward(completions, **kwargs): | |
| """Recompensează completările care urmează formatul dorit""" | |
| # Exemplu: Verifică dacă completarea urmează un format gândește-apoi-răspunde | |
| pattern = r"<think>(.*?)</think>\s*<answer>(.*?)</answer>" | |
| rewards = [] | |
| for completion in completions: | |
| match = re.search(pattern, completion, re.DOTALL) | |
| if match: | |
| # Verifică dacă există conținut substanțial în ambele secțiuni | |
| think_content = match.group(1).strip() | |
| answer_content = match.group(2).strip() | |
| if len(think_content) > 20 and len(answer_content) > 0: | |
| rewards.append(1.0) | |
| else: | |
| rewards.append( | |
| 0.5 | |
| ) # Recompensă parțială pentru format corect dar conținut limitat | |
| else: | |
| rewards.append(0.0) # Nicio recompensă pentru format incorect | |
| return rewards | |
| ``` | |
| <!-- # TODO: update links when PR is merged --> | |
| <iframe | |
| src="https://marimo.app/gh/huggingface/notebooks/main/e?entrypoint=course%2Fen%2Fchapter13%2Fgrpo_format.py&embed=true&show-chrome=false" | |
| title="Marimo Notebook" | |
| width="100%" | |
| height="800px" | |
| frameBorder="0" | |
| allow="clipboard-write" | |
| ></iframe> | |
| Aceste exemple demonstrează cum poți implementa funcții de recompensă inspirate din procesul de antrenare DeepSeek R1, concentrându-se pe corectitudine, formatare și semnale combinate. | |
| ## Asta e tot! | |
| În următoarea secțiune, vei urma un exercițiu pentru a implementa GRPO în TRL. | |
| <EditOnGithub source="https://github.com/huggingface/course/blob/main/chapters/ro/chapter12/4.mdx" /> |
Xet Storage Details
- Size:
- 9.33 kB
- Xet hash:
- 55247d53c78fdac3b746723e3ac6b83869530c0450341c162ba39c85b61a7eaf
·
Xet efficiently stores files, intelligently splitting them into unique chunks and accelerating uploads and downloads. More info.