kalkiek95 commited on
Commit
3ed708f
·
verified ·
1 Parent(s): e032c47

Update card: read feature names from model.config.id2label

Browse files
Files changed (1) hide show
  1. README.md +50 -40
README.md CHANGED
@@ -1,20 +1,27 @@
1
  # Neurobiber: Fast and Interpretable Stylistic Feature Extraction
2
 
3
- **Neurobiber** is a transformer-based model that quickly predicts **96 interpretable stylistic features** in text. These features are inspired by Biber’s multidimensional framework of linguistic style, capturing everything from **pronouns** and **passives** to **modal verbs** and **discourse devices**. By combining a robust linguistically informed feature set with the speed of neural inference, NeuroBiber enables large-scale stylistic analyses that were previously infeasible.
 
 
 
 
 
4
 
5
  ## Why Neurobiber?
6
 
7
- Extracting Biber-style features typically involves running a full parser or specialized tagger, which can be computationally expensive for large datasets or real-time applications. NeuroBiber overcomes these challenges by:
8
- - **Operating up to 56x faster** than parsing-based approaches.
9
- - Retaining the **interpretability** of classical Biber-like feature definitions.
10
- - Delivering **high accuracy** on diverse text genres (e.g., social media, news, literary works).
11
- - Allowing seamless integration with **modern deep learning** pipelines via Hugging Face.
12
 
13
- By bridging detailed linguistic insights and industrial-scale performance, Neurobiber supports tasks in register analysis, style transfer, and more.
 
 
 
14
 
15
  ## Example Script
16
 
17
- Below is an **example** showing how to load Neurobiber from Hugging Face, process single or multiple texts, and obtain a 96-dimensional binary vector for each input.
 
18
 
19
  ```python
20
  import torch
@@ -24,25 +31,6 @@ from transformers import AutoTokenizer, AutoModelForSequenceClassification
24
  MODEL_NAME = "Blablablab/neurobiber"
25
  CHUNK_SIZE = 512 # Neurobiber was trained with max_length=512
26
 
27
- # List of the 96 features that Neurobiber can predict
28
- BIBER_FEATURES = [
29
- "BIN_QUAN","BIN_QUPR","BIN_AMP","BIN_PASS","BIN_XX0","BIN_JJ",
30
- "BIN_BEMA","BIN_CAUS","BIN_CONC","BIN_COND","BIN_CONJ","BIN_CONT",
31
- "BIN_DPAR","BIN_DWNT","BIN_EX","BIN_FPP1","BIN_GER","BIN_RB",
32
- "BIN_PIN","BIN_INPR","BIN_TO","BIN_NEMD","BIN_OSUB","BIN_PASTP",
33
- "BIN_VBD","BIN_PHC","BIN_PIRE","BIN_PLACE","BIN_POMD","BIN_PRMD",
34
- "BIN_WZPRES","BIN_VPRT","BIN_PRIV","BIN_PIT","BIN_PUBV","BIN_SPP2",
35
- "BIN_SMP","BIN_SERE","BIN_STPR","BIN_SUAV","BIN_SYNE","BIN_TPP3",
36
- "BIN_TIME","BIN_NOMZ","BIN_BYPA","BIN_PRED","BIN_TOBJ","BIN_TSUB",
37
- "BIN_THVC","BIN_NN","BIN_DEMP","BIN_DEMO","BIN_WHQU","BIN_EMPH",
38
- "BIN_HDG","BIN_WZPAST","BIN_THAC","BIN_PEAS","BIN_ANDC","BIN_PRESP",
39
- "BIN_PROD","BIN_SPAU","BIN_SPIN","BIN_THATD","BIN_WHOBJ","BIN_WHSUB",
40
- "BIN_WHCL","BIN_ART","BIN_AUXB","BIN_CAP","BIN_SCONJ","BIN_CCONJ",
41
- "BIN_DET","BIN_EMOJ","BIN_EMOT","BIN_EXCL","BIN_HASH","BIN_INF",
42
- "BIN_UH","BIN_NUM","BIN_LAUGH","BIN_PRP","BIN_PREP","BIN_NNP",
43
- "BIN_QUES","BIN_QUOT","BIN_AT","BIN_SBJP","BIN_URL","BIN_WH",
44
- "BIN_INDA","BIN_ACCU","BIN_PGAS","BIN_CMADJ","BIN_SPADJ","BIN_X"
45
- ]
46
 
47
  def load_model_and_tokenizer():
48
  tokenizer = AutoTokenizer.from_pretrained(MODEL_NAME, use_fast=True)
@@ -50,12 +38,14 @@ def load_model_and_tokenizer():
50
  model.eval()
51
  return model, tokenizer
52
 
 
53
  def chunk_text(text, chunk_size=CHUNK_SIZE):
54
  tokens = text.strip().split()
55
  if not tokens:
56
  return []
57
  return [" ".join(tokens[i:i + chunk_size]) for i in range(0, len(tokens), chunk_size)]
58
 
 
59
  def get_predictions_chunked_batch(model, tokenizer, texts, chunk_size=CHUNK_SIZE, subbatch_size=32):
60
  chunked_texts = []
61
  chunk_indices = []
@@ -104,27 +94,32 @@ def get_predictions_chunked_batch(model, tokenizer, texts, chunk_size=CHUNK_SIZE
104
 
105
  return np.array(predictions)
106
 
 
107
  def predict_batch(model, tokenizer, texts, chunk_size=CHUNK_SIZE, subbatch_size=32):
108
  return get_predictions_chunked_batch(model, tokenizer, texts, chunk_size, subbatch_size)
109
 
 
110
  def predict_text(model, tokenizer, text, chunk_size=CHUNK_SIZE, subbatch_size=32):
111
  batch_preds = predict_batch(model, tokenizer, [text], chunk_size, subbatch_size)
112
  return batch_preds[0]
113
  ```
114
 
115
  ## Single-Text Usage
116
- ``` python
 
117
  model, tokenizer = load_model_and_tokenizer()
118
  sample_text = "This is a sample text demonstrating certain stylistic features."
119
  predictions = predict_text(model, tokenizer, sample_text)
120
- print("Binary feature vector:", predictions)
121
- # For example: [0, 1, 0, 1, ... 1, 0] (96-length)
122
 
 
 
 
 
123
  ```
124
 
125
  ## Batch Usage
126
- ``` python
127
 
 
128
  docs = [
129
  "First text goes here.",
130
  "Second text, slightly different style."
@@ -132,20 +127,35 @@ docs = [
132
  model, tokenizer = load_model_and_tokenizer()
133
  preds = predict_batch(model, tokenizer, docs)
134
  print(preds.shape) # (2, 96)
135
- ```
136
 
 
 
 
 
 
137
 
138
  ## How It Works
139
 
140
- Neurobiber is fine-tuned RoBERTa. Given a text:
141
- 1. The text is split into **chunks** (up to 512 tokens each).
142
- 2. Each chunk is fed through the model to produce **96 logistic outputs** (one per feature).
143
- 3. The feature probabilities are aggregated across chunks so that each feature is marked as `1` if it appears in at least one chunk.
 
 
 
 
 
144
 
145
- Each row in preds is a 96-element array corresponding to the feature order in BIBER_FEATURES.
146
 
147
- Interpreting Outputs
 
 
 
148
 
149
- - Each element in the vector is a binary label (0 or 1), indicating the model’s detection of a specific linguistic feature (e.g., BIN_VBD for past tense verbs).
150
- - For long texts, we chunk them into segments of length 512 tokens. If a feature appears in any chunk, you get a 1 for that feature.
151
 
 
 
 
 
 
1
  # Neurobiber: Fast and Interpretable Stylistic Feature Extraction
2
 
3
+ Neurobiber is a transformer-based model that quickly predicts 96 interpretable
4
+ stylistic features in text. These features are inspired by Biber's
5
+ multidimensional framework of linguistic style, capturing everything from
6
+ pronouns and passives to modal verbs and discourse devices. By combining a robust
7
+ linguistically informed feature set with the speed of neural inference, Neurobiber
8
+ enables large-scale stylistic analyses that were previously infeasible.
9
 
10
  ## Why Neurobiber?
11
 
12
+ Extracting Biber-style features typically involves running a full parser or
13
+ specialized tagger, which can be computationally expensive for large datasets or
14
+ real-time applications. Neurobiber overcomes these challenges by:
 
 
15
 
16
+ - Operating up to 56x faster than parsing-based approaches.
17
+ - Retaining the interpretability of classical Biber-like feature definitions.
18
+ - Delivering high accuracy on diverse text genres (e.g., social media, news, literary works).
19
+ - Allowing seamless integration with modern deep learning pipelines via Hugging Face.
20
 
21
  ## Example Script
22
 
23
+ The model now ships the feature names in its config, so you can map each output
24
+ dimension to its feature via `model.config.id2label` - no manual feature list.
25
 
26
  ```python
27
  import torch
 
31
  MODEL_NAME = "Blablablab/neurobiber"
32
  CHUNK_SIZE = 512 # Neurobiber was trained with max_length=512
33
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
34
 
35
  def load_model_and_tokenizer():
36
  tokenizer = AutoTokenizer.from_pretrained(MODEL_NAME, use_fast=True)
 
38
  model.eval()
39
  return model, tokenizer
40
 
41
+
42
  def chunk_text(text, chunk_size=CHUNK_SIZE):
43
  tokens = text.strip().split()
44
  if not tokens:
45
  return []
46
  return [" ".join(tokens[i:i + chunk_size]) for i in range(0, len(tokens), chunk_size)]
47
 
48
+
49
  def get_predictions_chunked_batch(model, tokenizer, texts, chunk_size=CHUNK_SIZE, subbatch_size=32):
50
  chunked_texts = []
51
  chunk_indices = []
 
94
 
95
  return np.array(predictions)
96
 
97
+
98
  def predict_batch(model, tokenizer, texts, chunk_size=CHUNK_SIZE, subbatch_size=32):
99
  return get_predictions_chunked_batch(model, tokenizer, texts, chunk_size, subbatch_size)
100
 
101
+
102
  def predict_text(model, tokenizer, text, chunk_size=CHUNK_SIZE, subbatch_size=32):
103
  batch_preds = predict_batch(model, tokenizer, [text], chunk_size, subbatch_size)
104
  return batch_preds[0]
105
  ```
106
 
107
  ## Single-Text Usage
108
+
109
+ ```python
110
  model, tokenizer = load_model_and_tokenizer()
111
  sample_text = "This is a sample text demonstrating certain stylistic features."
112
  predictions = predict_text(model, tokenizer, sample_text)
 
 
113
 
114
+ # Map the 96-dim binary vector to feature names straight from the model config.
115
+ present = {model.config.id2label[i]: int(v) for i, v in enumerate(predictions)}
116
+ print(present) # {'BIN_QUAN': 0, 'BIN_QUPR': 1, ...}
117
+ print([f for f, v in present.items() if v]) # just the detected features
118
  ```
119
 
120
  ## Batch Usage
 
121
 
122
+ ```python
123
  docs = [
124
  "First text goes here.",
125
  "Second text, slightly different style."
 
127
  model, tokenizer = load_model_and_tokenizer()
128
  preds = predict_batch(model, tokenizer, docs)
129
  print(preds.shape) # (2, 96)
 
130
 
131
+ # Names for any row come from the config:
132
+ id2label = model.config.id2label
133
+ for row in preds:
134
+ print([id2label[i] for i, v in enumerate(row) if v])
135
+ ```
136
 
137
  ## How It Works
138
 
139
+ Neurobiber is a fine-tuned RoBERTa. Given a text:
140
+
141
+ 1. The text is split into chunks (up to 512 tokens each).
142
+ 2. Each chunk is fed through the model to produce 96 logistic outputs (one per feature).
143
+ 3. The feature probabilities are aggregated across chunks so that each feature is
144
+ marked as `1` if it appears in at least one chunk.
145
+
146
+ Each row in `preds` is a 96-element array. The mapping from index to feature name
147
+ is published in `model.config.id2label` (and the reverse in `model.config.label2id`).
148
 
149
+ ### Interpreting Outputs
150
 
151
+ - Each element is a binary label (0 or 1) indicating the model's detection of a
152
+ specific linguistic feature (e.g., `BIN_VBD` for past tense verbs).
153
+ - For long texts, segments of length 512 tokens are scored independently; if a
154
+ feature appears in any chunk, the output is `1` for that feature.
155
 
156
+ ## Note on Feature Names
 
157
 
158
+ The 96 features and their order are defined by biberplus
159
+ (`biberplus.tagger.constants.BIBER_PLUS_TAGS`, prefixed with `BIN_`) and match the
160
+ training label order. This mapping is embedded in the model config, so prefer
161
+ `model.config.id2label` over any hardcoded list.