heal 0 0 0

argilla/distilabel-intel-orca-dpo-pairs

published by @argilla

Alignment dataset tracked in the /datasets sub-catalog.

Lifetime downloads
185.3K
Last 30 days
17.2K
Likes
185
Size
75.6 MB
Created on HF
2024-01-07
Age
2 years ago

Description

distilabel Orca Pairs for DPO

The dataset is a "distilabeled" version of the widely used dataset: Intel/orca_dpo_pairs. The original dataset has been used by 100s of open-source practitioners and models. We knew from fixing UltraFeedback (and before that, Alpacas and Dollys) that this dataset could be highly improved.

Continuing with our mission to build the best alignment datasets for open-source LLMs and the community, we spent a few hours improving it with… See the full description on the dataset page: https://huggingface.co/datasets/argilla/distilabel-intel-orca-dpo-pairs.

Tags

license:apache-2.0size_categories:10K<n<100Kformat:parquetmodality:textlibrary:datasetslibrary:pandaslibrary:mlcroissantlibrary:polarsregion:us

README current version from Hugging Face


license: apache-2.0

Built with Distilabel

distilabel Orca Pairs for DPO

The dataset is a "distilabeled" version of the widely used dataset: Intel/orca_dpo_pairs. The original dataset has been used by 100s of open-source practitioners and models. We knew from fixing UltraFeedback (and before that, Alpacas and Dollys) that this dataset could be highly improved.

Continuing with our mission to build the best alignment datasets for open-source LLMs and the community, we spent a few hours improving it with distilabel.

This was our main intuition: the original dataset just assumes gpt4/3.5-turbo are always the best response. We know from UltraFeedback that's not always the case. Moreover, DPO fine-tuning benefits from the diversity of preference pairs.

Additionally, we have added a new column indicating whether the question in the dataset is part of the train set of gsm8k (there were no examples from the test set). See the reproduction section for more details.

Using this dataset

This dataset is useful for preference tuning and we recommend using it instead of the original. It's already prepared in the "standard" chosen, rejected format with additional information for further filtering and experimentation.

The main changes are:

  1. ~2K pairs have been swapped: rejected become the chosen response. We have kept the original chosen and rejected on two new columns original_* for reproducibility purposes.
  2. 4K pairs have been identified as tie: equally bad or good.
  3. Chosen scores have been added: you can now filter out based on a threshold (see our distilabeled Hermes 2.5 model for an example)
  4. We have kept the ratings and rationales generated with gpt-4-turbo and distilabel so you can prepare the data differently if you want.
  5. We have added a column to indicate if the input is part of gsm8k train set.

In our experiments, we have got very good results by reducing the size of the dataset by more than 50%. Here's an example of how to achieve that:

from datasets import load_dataset

# Instead of this:
# dataset = load_dataset("Intel/orca_dpo_pairs", split="train")

# use this:
dataset = load_dataset("argilla/distilabel-intel-orca-dpo-pairs", split="train")

dataset = dataset.filter(
    lambda r: 
        r["status"] != "tie" and 
        r["chosen_score"] >= 8 and 
        not r["in_gsm8k_train"]
)

This results in 5,922 instead of 12,859 samples (54% reduction) and leads to better performance than the same model tuned with 100% of the samples in the original dataset.

We'd love to hear about your experiments! If you want to try this out, consider joining our Slack community and let's build some open datasets and models together.

Reproducing the dataset

In this section, we outline the steps to reproduce this dataset.

Rate original dataset pairs

Build a preference dataset with distilabel using the original dataset:

from distilabel.llm import OpenAILLM
from distilabel.tasks import JudgeLMTask
from distilabel.pipeline import Pipeline

from datasets import load_dataset

# Shuffle 'chosen' and 'rejected' to avoid positional bias and keep track of the order
def shuffle_and_track(chosen, rejected):
    pair = [chosen, rejected]
    random.shuffle(pair)
    order = ["chosen" if x == chosen else "rejected" for x in pair]
    return {"generations": pair, "order": order}

dataset = load_dataset("Intel/orca_dpo_pairs", split="train")

# This shuffles the pairs to mitigate positional bias
dataset = dataset.map(lambda x: shuffle_and_track(x["chosen"], x["rejected"]))

# We use our JudgeLM implementation to rate the original pairs
labeler = OpenAILLM(
    task=JudgeLMTask(),
    model="gpt-4-1106-preview",
    num_threads=16,
    max_new_tokens=512,
)

dataset = dataset.rename_columns({"question": "input"})

distipipe = Pipeline(
    labeller=labeler
)

# This computes ratings and natural language critiques for each pair
ds = distipipe.generate(dataset=dataset, num_generations=2)

If you want to further filter and curate the dataset, you can push the dataset to Argilla as follows:

rg_dataset = ds.to_argilla()

rg_dataset.push_to_argilla(name="your_dataset_name", workspace="your_workspace_name")

You get a nice UI with a lot of pre-computed metadata to explore and curate the dataset:

image/png

The resulting dataset is now much more useful: we know which response is preferred (by gpt-4-turbo), which ones have low scores, and we even have natural language explanations. But what did we find? Was our intuition confirmed?

image/png

The above chart shows the following:

  • ~4,000 pairs were given the same rating (a tie).
  • ~7,000 pairs were correct according to our AI judge (unchanged).
  • and ~2,000 times the rejected response was preferred (swapped).

Now the next question is: can we build better models with this new knowledge? The answer is the "distilabeled Hermes" model, check it out!

Post-processing to add useful information

Swap rejected and chosen, and add chosen scores and status:

def add_status(r):
  status = "unchanged"
  highest_rated_idx = np.argmax(r['rating'])
  # Compare to the index of the chosen response
  if r['rating']== None or r['rating'][0] == r['rating'][1]:
    status = "tie"
  elif r['order'][highest_rated_idx] != 'chosen':
      status = "swapped"
  return {"status": status}

def swap(r):
  chosen = r["chosen"]
  rejected = r["rejected"]
  if r['rating'] is not None:
    chosen_score = r['rating'][np.argmax(r['rating'])]
  else:
    chosen_score = None
  if r['status'] == "swapped":
    chosen = r["rejected"]
    rejected = r["chosen"]
  return {
      "chosen": chosen,
      "rejected": rejected,
      "original_chosen": r["chosen"],
      "original_rejected": r["rejected"],
      "chosen_score": chosen_score
  }

updated = ds.map(add_status).map(swap)

gsm8k "decontamination"

The basic approach for finding duplicated examples. We didn't find any from the test sets. We experimented with lower thresholds but below 0.8 they introduced false positives:

import pandas as pd

import nltk
from sklearn.feature_extraction.text import TfidfVectorizer
from sklearn.metrics.pairwise import cosine_similarity

from datasets import load_dataset

nltk.download('punkt')

# Load the datasets
source_dataset = load_dataset("gsm8k", "main", split="train")
source_dataset_socratic = load_dataset("gsm8k", "socratic", split="train")
#target_dataset = load_dataset("Intel/orca_dpo_pairs", split="train")
target_dataset = load_dataset("argilla/distilabel-intel-orca-dpo-pairs", split="train")

# Extract the 'question' column from each dataset
source_questions = source_dataset['question']
source_questions_socratic = source_dataset_socratic['question']
target_questions = target_dataset['input']

# Function to preprocess the text
def preprocess(text):
    return nltk.word_tokenize(text.lower())

# Preprocess the questions
source_questions_processed = [preprocess(q) for q in source_questions]
source_questions.extend([preprocess(q) for q in source_questions_socratic])
target_questions_processed = [preprocess(q) for q in target_questions]


# Vectorize the questions
vectorizer = TfidfVectorizer()
source_vec = vectorizer.fit_transform([' '.join(q) for q in source_questions_processed])
target_vec = vectorizer.transform([' '.join(q) for q in target_questions_processed])

# Calculate cosine similarity
similarity_matrix = cosine_similarity(source_vec, target_vec)

# Determine matches based on a threshold:
# checked manually and below 0.8 there are only false positives
threshold = 0.8
matching_pairs = []
for i, row in enumerate(similarity_matrix):
    for j, similarity in enumerate(row):
        if similarity >= threshold:
            matching_pairs.append((source_questions[i], target_questions[j], similarity))

# Create a DataFrame from the matching pairs
df = pd.DataFrame(matching_pairs, columns=['Source Question', 'Target Question', 'Similarity Score'])

# Create a set of matching target questions
matching_target_questions = list(df['Target Question'])

# Add a column to the target dataset indicating whether each question is matched
target_dataset = target_dataset.map(lambda example: {"in_gsm8k_train": example['input'] in matching_target_questions})

Result:

False    12780
True        79
Name: in_gsm8k_train

README history 17 revisions

Every night we snapshot the README of every dataset in the catalog. When the SHA changes we archive the new version and diff it against the last. This is the evolving thought record of the alignment-data field: what the author decided to say about the corpus, and how that framing shifted over time.

  1. 2025-08-07Update README.md0b10ec08.8 KB
    Loading...
  2. 2025-03-19Update README.md0ac12519.9 KB
    Loading...
  3. 2024-02-05Update README.md1d2f15f9.8 KB
    Loading...
  4. 2024-01-22Update README.md081de909.8 KB
    Loading...
  5. 2024-01-22Update README.mde9890b99.8 KB
    Loading...
  6. 2024-01-10Update README.mdae5268f9.9 KB
    Loading...
  7. 2024-01-10Update README.md97a8e529.4 KB
    Loading...
  8. 2024-01-10Update README.md35393289.4 KB
    Loading...
  9. 2024-01-10Update README.mdeda9b7b9.4 KB
    Loading...
  10. 2024-01-09Upload dataset40532391.2 KB
    Loading...
  11. 2024-01-09Update README.md818018d1.2 KB
    Loading...
  12. 2024-01-09Update README.mdac015a0995 B
    Loading...
  13. 2024-01-08Upload dataset1d46f6e921 B
    Loading...
  14. 2024-01-08Upload dataset20b679a879 B
    Loading...
  15. 2024-01-07Upload datasetb60f7da789 B
    Loading...
  16. 2024-01-07Upload datasete85a2a4754 B
    Loading...
  17. 2024-01-07initial commitf1f2cbe0 B
    Loading...

Used by abliterated models none yet

No abliterated models in our catalog have declared this dataset in their YAML metadata yet. This can mean the dataset is used but not declared, is used outside abliteration workflows, or is new. The link will populate automatically as models are indexed.

Used in recipes 1 of 18 curated recipes reference this dataset

Concrete workflows from the community craft-knowledge survey that call for this corpus. Each links to the full recipe with parameters, tools, expected output, and known failure modes.

Derived corpora 1 dataset in the catalog cite this one

Other datasets in the catalog whose description names this one as a source (`based on`, `derived from`, `extended from`, `subset of`, `translated from`, etc.). This is the lineage-hint layer that complements the "Used by models" section above: many models cite the derived corpus rather than this root.

Community discussions 3 threads · 3 open · 4 comments

Threads posted by the community on Hugging Face: bug reports, questions about usage, pull requests on the README, license clarifications. Click any thread to expand and read the full conversation inline. Newest first.

  1. 2025-03-20[bot] Conversion to Parquetopen1 💬#3
    Loading...
  2. 2024-03-09PRUpdate licenseopen1 💬#2
    Loading...
  3. 2024-01-27chosen 6k DPO pairs bias towards translation?open2 💬#1
    Loading...

Related datasets same stage · heal

Read further

Metadata

License
apache-2.0

Repository

Download the dataset

0

Copy any of these snippets into your notebook or terminal. All three fetch directly from Hugging Face using your own credentials.

Recommended: datasets library (Python)
from datasets import load_dataset
ds = load_dataset("argilla/distilabel-intel-orca-dpo-pairs")
Raw snapshot (Python)
from huggingface_hub import snapshot_download
snapshot_download(repo_id="argilla/distilabel-intel-orca-dpo-pairs", repo_type="dataset")
git clone (requires git-lfs)
git clone https://huggingface.co/datasets/argilla/distilabel-intel-orca-dpo-pairs
Catalog is the map. Apps are the tools.

Run models on your own machine, not in the cloud.

Every model page has an "Open in Abliteration" button that hands the model directly to the first-party desktop client, at the quantization your rig can actually run. No API keys, no subscription, no prompt leakage.

Open in Abliteration