5

Computing the semantic similarity between two synsets in WordNet can be easily done with several built-in similarity measures, such as:

synset1.path_similarity(synset2)

synset1.lch_similarity(synset2), Leacock-Chodorow Similarity

synset1.wup_similarity(synset2), Wu-Palmer Similarity

(as seen here)

However, all of these exploit WordNet's taxonomic relations, which are relations for nouns and verbs. Adjectives and adverbs are related via synonymy, antonymy and pertainyms. How can one measure the distance (number of hops) between two adjectives?

I tried path_similarity(), but as expected, it returns 'None':

from nltk.corpus import wordnet as wn
x = wn.synset('good.a.01')
y = wn.synset('bad.a.01')


print(wn.path_similarity(x,y))

If there is any way to compute the distance between one adjective and another, pointing it out would be greatly appreciated.

Community
  • 1
  • 1
modarwish
  • 495
  • 10
  • 22

2 Answers2

7

There's no easy way to get similarity between words that are not nouns/verbs.

As noted, nouns/verbs similarity are easily extracted from

>>> from nltk.corpus import wordnet as wn
>>> dog = wn.synset('dog.n.1')
>>> cat = wn.synset('cat.n.1')
>>> car = wn.synset('car.n.1')
>>> wn.path_similarity(dog, cat)
0.2
>>> wn.path_similarity(dog, car)
0.07692307692307693
>>> wn.wup_similarity(dog, cat)
0.8571428571428571
>>> wn.wup_similarity(dog, car)
0.4
>>> wn.lch_similarity(dog, car)
1.072636802264849
>>> wn.lch_similarity(dog, cat)
2.0281482472922856

For adjective it's hard, so you would need to build your own text similarity device. The easiest way is to use vector space model, basically, all words are represented by a number of floating point numbers, e.g.

>>> import numpy as np
>>> blue = np.array([0.2, 0.2, 0.3])
>>> red = np.array([0.1, 0.2, 0.3])
>>> pink = np.array([0.1001, 0.221, 0.321])
>>> car = np.array([0.6, 0.9, 0.5])
>>> def cosine(x,y):
...     return np.dot(x,y) / (np.linalg.norm(x) * np.linalg.norm(y))
... 
>>> cosine(pink, red)
0.99971271929384864
>>> cosine(pink, blue)
0.96756147991512709
>>> cosine(blue, red)
0.97230558532824662
>>> cosine(blue, car)
0.91589118863996888
>>> cosine(red, car)
0.87469454283170045
>>> cosine(pink, car)
0.87482313596223782

To train a bunch of vectors for something like pink = np.array([0.1001, 0.221, 0.321]), you should try google for

  • Latent semantic indexing / Latent semantic analysis
  • Bag of Words
  • Vector space model semantics
  • Word2Vec, Doc2Vec, Wiki2Vec
  • Neural Nets
  • cosine similarity natural language semantics

You can also try some off the shelf software / libraries like:

Other than vector space model, you can try some graphical model that puts words into a graph and uses something like pagerank to walk around the graph to give you some similarity measure.

See also:

Community
  • 1
  • 1
alvas
  • 115,346
  • 109
  • 446
  • 738
  • Thanks for the advice. There is a paper by Kamps et al. (2004), in which they determine the polarity (has a positive or negative sentiment) of adjectives within WordNet. They do this by measuring distance(adj1, bad) subtracted by distance(adj1, bad). So they talk about this in their paper, but I am not sure how the heck they have implemented this!! Any thoughts? [Link to paper](http://humanities.uva.nl/~kamps/publications/2004/kamp:usin04.pdf) @alvas – modarwish Jul 05 '15 at 20:13
  • 1
    they seem to build a graph and then use graph distance measures but i'm not exactly sure what they did. Possibly you can email the authors ;P – alvas Jul 05 '15 at 20:32
2

In the paper by Kamps et al. (2004), they defined a graph of words as nodes which nodes are connected if two words are synonyms. Then they defined shortest path between two words as their geodesic distance. As I understand, there is no weight on edges, which means you basically can count number of edges when you want to find the shortest path.

The paper:

Kamps, Jaap, et al. "Using WordNet to Measure Semantic Orientations of Adjectives." LREC. Vol. 4. 2004.

But what they really seeking is a measure for semantic orientation. It depends on your application to choose the best measure accordingly. A set of similarity measures which recently achieved a huge attention is based on Distributional Hypothesis. These machine learning methods based on word usages in huge documents create geometric similarity measures (e.g. cosine similarity). But these methods are conceptually disconnected from WordNet distance measures.

However, there are some works around it to use WordNet gloss and definitions in synsets as context samples to learn statistical models of words such as Patwardhan and Pedersen (2006). But in general these model are not suitable for finding sentiment orientations without supervision of positiveness or negativeness.

Mehdi
  • 4,202
  • 5
  • 20
  • 36
  • Yes, I have explored various semantic similarity measures, and used them to tag a word as positive or negative. I have tried WordNet distance, supervised classification with synsets as features, or with gloss info as features, random walks, ensembles, morphological affix modifications, affect info, and corpus/statistical based. But I am currently working on WordNet distance based measures of adjectives to tag words with a semantic orientation (polarity). So this is why I am only interested in distance of adjectives. I guess I will have develop a code to count edges. Thanks @Mehdi – modarwish Jul 05 '15 at 22:40
  • 1
    I think it takes a pretty heavy computation if you build all the graph and then find the shortest path. So far, they had limited test set, with limited goal just for sake of their point in the paper. If you found it hard to implement the shortest path in the graph, maybe you can use *random walk* model instead of shortest path. I found this paper very related to the idea of using graph of WordNet: http://nlp.stanford.edu/pubs/wordwalk-textgraphs09.pdf – Mehdi Jul 05 '15 at 22:55