Repository: huggingface/transformers (Python)
Date: 2020-03-05 21:15:10+00:00
Task type: Bug Fix

Issue:
wrong 'label2id' and 'id2label' in config when loading from pretrained
# 🐛 Bug

## Information

Model I am using (Bert, XLNet ...): Bert

Language I am using the model on (English, Chinese ...): English

The problem arises when using:
* [ ] the official example scripts: (give details below)
* [x] my own modified scripts: (give details below)

The tasks I am working on is:
* [ ] an official GLUE/SQUaD task: (give the name)
* [x] my own task or dataset: (give details below)

## To reproduce

Steps to reproduce the behavior:

1. 
```python
from transformers import BertConfig
config = BertConfig.from_pretrained('bert-base-cased', num_labels=3)
print(config.id2label)
```
2. Prints: {0: 'LABEL_0', 1: 'LABEL_1'}


<!-- If you have code snippets, error messages, stack traces please provide them here as well.
     Important! Use code tags to correctly format your code. See https://help.github.com/en/github/writing-on-github/creating-and-highlighting-code-blocks#syntax-highlighting
     Do not use screenshots, as they are hard to read and (more importantly) don't allow others to copy-and-paste your code.-->

## Expected behavior

<!-- A clear and concise description of what you would expect to happen. -->

prints {0: 'LABEL_0', 1: 'LABEL_1', 2: 'LABEL_2'}

## Environment info
<!-- You can run the command `python transformers-cli env` and copy-and-paste its output below.
     Don't forget to fill out the missing fields in that output! -->
     
- `transformers` version: 2.5.1
- Platform: Ubuntu 16.04
- Python version: 3.7.6
- PyTorch version (GPU?): 1.4.0
- Using GPU in script?: no
- Using distributed or parallel set-up in script?: no



Issue discussion:

Solution patch:
diff --git a/src/transformers/configuration_utils.py b/src/transformers/configuration_utils.py
--- a/src/transformers/configuration_utils.py
+++ b/src/transformers/configuration_utils.py
@@ -98,6 +98,18 @@ def __init__(self, **kwargs):
                 logger.error("Can't set {} with value {} for {}".format(key, value, self))
                 raise err
 
+    @property
+    def num_labels(self):
+        return self._num_labels
+
+    @num_labels.setter
+    def num_labels(self, num_labels):
+        self._num_labels = num_labels
+        self.id2label = {i: "LABEL_{}".format(i) for i in range(self.num_labels)}
+        self.id2label = dict((int(key), value) for key, value in self.id2label.items())
+        self.label2id = dict(zip(self.id2label.values(), self.id2label.keys()))
+        self.label2id = dict((key, int(value)) for key, value in self.label2id.items())
+
     def save_pretrained(self, save_directory):
         """
         Save a configuration object to the directory `save_directory`, so that it


Test patch:
diff --git a/tests/test_configuration_common.py b/tests/test_configuration_common.py
--- a/tests/test_configuration_common.py
+++ b/tests/test_configuration_common.py
@@ -57,8 +57,18 @@ def create_and_test_config_from_and_save_pretrained(self):
 
         self.parent.assertEqual(config_second.to_dict(), config_first.to_dict())
 
+    def create_and_test_config_with_num_labels(self):
+        config = self.config_class(**self.inputs_dict, num_labels=5)
+        self.parent.assertEqual(len(config.id2label), 5)
+        self.parent.assertEqual(len(config.label2id), 5)
+
+        config.num_labels = 3
+        self.parent.assertEqual(len(config.id2label), 3)
+        self.parent.assertEqual(len(config.label2id), 3)
+
     def run_common_tests(self):
         self.create_and_test_config_common_properties()
         self.create_and_test_config_to_json_string()
         self.create_and_test_config_to_json_file()
         self.create_and_test_config_from_and_save_pretrained()
+        self.create_and_test_config_with_num_labels()