Skip to content
NLP · 3 of 4 · Python

Classify a sentiment baseline

Here is a whole text classifier in a few lines. Give every word a score: positive for words like great, negative for words like bad. To judge a text, add up the scores of its words. Above 0 the text is positive, below 0 negative. It is fast and you can see exactly why it gave its answer. It is also easy to fool, and knowing how is the point of this lesson.

Learn it

Words to know

baseline
A simple model that sets the score a more complex model has to beat.
bias
A number added after the weighted sum. It lets the result be something other than 0 when every input is 0.
bag of words
A text described only by how often each word appears. Word order is ignored.

How it works

  1. Lowercase the text and split it on whitespace, as in the last lesson.
  2. Start the score at bias. For each word, add its score from lexicon. A word that is not in the lexicon adds 0.
  3. A word that appears twice is counted twice.
  4. Return positive if the score is above 0, negative if it is below 0, and neutral if it is exactly 0.

Worked example

Input
text = "great food bad service"
lexicon = {"great": 2, "bad": -1}
bias = 0

Output
"positive"
WordScoreRunning total
great22
food0 (not listed)2
bad-11
service0 (not listed)1

The total is 1, above 0, so the answer is positive. The model has no idea which word described which thing.

Why it matters

Every stronger model should be compared with a simple baseline like this on the same data. If the big model is not clearly better, it is not worth its cost.

Your turn

Classify a text as positive, negative or neutral by adding up word scores.

text
any string
lexicon
a dictionary from lowercase word to its score
bias
a number the score starts from
Returns
"positive" when the total is above 0, "negative" when it is below 0, "neutral" when it is exactly 0.

Example 1

Input
text = "great food bad service"
lexicon = {"great": 2, "bad": -1}
bias = 0

Output
"positive"

great adds 2 and bad takes away 1. The total is 1, so the text is positive.

Example 2

Input
text = "not bad"
lexicon = {"good": 2, "bad": -2}
bias = 0

Output
"negative"

A person reads this as mild praise. The model sees only bad, with a score of -2, and says negative.

Example 3

Input
text = "Good good bad"
lexicon = {"good": 1, "bad": -1}
bias = 0

Output
"positive"

Lowercased, good counts twice, 2, and bad once, -1. The total is 1.

Example 4

Input
text = "good day"
lexicon = {"good": 1}
bias = -2

Output
"negative"

good adds 1 to a bias of -2. The total is -1, so the text is negative.

Example 5

Input
text = "unknown"
lexicon = {}
bias = 0

Output
"neutral"

No word is in the lexicon and the bias is 0, so the total is exactly 0.

Hints

Each hint gives away a little more. Open one only when you need it.

  1. Hint 1: Where to start

    Keep one running total. Every word either adds its score to it or adds nothing.

  2. Hint 2: The key step

    lexicon.get(word, 0) gives a word's score, or 0 when the word is not listed. Start the total at bias.

  3. Hint 3: The outline

    Set score = bias. For each word in text.lower().split(), add lexicon.get(word, 0). Return "positive" if score > 0, "negative" if score < 0, otherwise "neutral".

Solution

From here on the page gives the method away. If you are still solving, go back to the hints.

Step by step

  1. The score starts at the bias. A bias above 0 makes the model lean positive before it has read a word, which is useful when most texts are positive.
  2. Each word adds its score; an unknown word adds 0. get with a default of 0 means a word outside the lexicon neither helps nor hurts.
  3. The sign of the total is the answer. Exactly 0 is its own case. Neither strict comparison is true there, so the last line answers neutral.

The same numbered steps are the comments in the solution.

Python
def solve(text, lexicon, bias):
    # 1. The score starts at the bias
    score = bias
    # 2. Each word adds its score; an unknown word adds 0
    for word in text.lower().split():
        score += lexicon.get(word, 0)
    # 3. The sign of the total is the answer
    if score > 0:
        return "positive"
    if score < 0:
        return "negative"
    return "neutral"

Watch out

  • Do not use lexicon[word]. It raises KeyError for the first word that is not in the lexicon.
  • The model cannot read context. not bad scores the same as bad, and sarcasm goes straight past it.

Check yourself

Why does this model get not bad wrong?

It scores each word alone and adds the scores up. It has no way to let not change the meaning of the word after it.

What is a baseline for?

It is a simple model to compare against. A more complex model has to beat it on the same data to be worth using.