Sentiment Analysis using StanfordCoreNLP in Java

Introduction
Introduction

Doing sentiment analysis on your own data isn’t a difficult process anymore, we have some fantastic libraries to make the process immensely easy. let’s start by applying basic sentiment analysis to this data:

I have taken iPhone X (Silver) User Review from Amazon

String text = "Just love the X. Feel so Premium and a Head turner too. Face ID working fine but still miss "
 + "the fingerprint scanner very much. I jump from 5S to X so it’s a huge skip. I’m very very happy" + " with it. Specially battery backup is great after using with 4g cellular network and no heating " + "issue at all, though I’m not a mobile gamer, Oftentimes I play Boom Beach and I watch YouTube " + "videos and I surf a lot. It makes a deep hole in pocket at the Hefty price tag. So it’s all " + "upto your Consideration.n";

If you are not familiar with StanfordCoreNLP, you can read Stanford CoreNLP Tutorial from here.

Sentiment Classification
Sentiment Classification



package com.interviewBubble.sentimentanalysis;public class SentimentClassification { /*  * "Very negative" = 0  * "Negative" = 1  * "Neutral" = 2  * "Positive" = 3  * "Very positive" = 4  */ int veryPositive; int positive; int neutral; int negative; int veryNegative; public int getVeryPositive() {  return veryPositive; } public void setVeryPositive(int veryPositive) {  this.veryPositive = veryPositive; } public int getPositive() {  return positive; } public void setPositive(int positive) {  this.positive = positive; } public int getNeutral() {  return neutral; } public void setNeutral(int neutral) {  this.neutral = neutral; } public int getNegative() {  return negative; } public void setNegative(int negative) {  this.negative = negative; } public int getVeryNegative() {  return veryNegative; } public void setVeryNegative(int veryNegative) {  this.veryNegative = veryNegative; }}


Sentiment Result
Sentiment Result

package com.interviewBubble.sentimentanalysis;public class SentimentResult { String sentimentType; int sentimentScore; SentimentClassification sentimentClass; public String getSentimentType() {  return sentimentType; } public void setSentimentType(String sentimentType) {  this.sentimentType = sentimentType; } public int getSentimentScore() {  return sentimentScore; } public void setSentimentScore(int sentimentScore) {  this.sentimentScore = sentimentScore; } public SentimentClassification getSentimentClass() {  return sentimentClass; } public void setSentimentClass(SentimentClassification sentimentClass) {  this.sentimentClass = sentimentClass; }}

Sentiment Analyzer
Sentiment Analyzer

package com.interviewBubble.sentimentanalysis;

import java.util.Properties;

import org.ejml.simple.SimpleMatrix;

import edu.stanford.nlp.ling.CoreAnnotations;

import edu.stanford.nlp.neural.rnn.RNNCoreAnnotations;

import edu.stanford.nlp.pipeline.Annotation;

import edu.stanford.nlp.pipeline.StanfordCoreNLP;

import edu.stanford.nlp.sentiment.SentimentCoreAnnotations;

import edu.stanford.nlp.trees.Tree;

import edu.stanford.nlp.util.CoreMap;

public class SentimentAnalyzer {

StanfordCoreNLP pipeline;

public void initialize() {

Properties properties = new Properties();

properties.setProperty("annotators", "tokenize, ssplit, parse, sentiment");

pipeline = new StanfordCoreNLP(properties);

}

public SentimentResult getSentimentResult(String text) {

SentimentClassification classification = new SentimentClassification();

SentimentResult sentimentResult = new SentimentResult();

if (text != null && text.length() > 0) {

Annotation annotation = pipeline.process(text);

for(CoreMap sentence: annotation.get(CoreAnnotations.SentencesAnnotation.class)) {

    // System.out.println(sentence);

Tree tree = sentence.get(SentimentCoreAnnotations.SentimentAnnotatedTree.class);

//System.out.println(tree);

SimpleMatrix simpleMatrix = RNNCoreAnnotations.getPredictions(tree);

//System.out.println(simpleMatrix);

classification.setVeryNegative((int)Math.round(simpleMatrix.get(0)*100d));

classification.setNegative((int)Math.round(simpleMatrix.get(1)*100d));

classification.setNeutral((int)Math.round(simpleMatrix.get(2)*100d));

classification.setPositive((int)Math.round(simpleMatrix.get(3)*100d));

classification.setVeryPositive((int)Math.round(simpleMatrix.get(4)*100d));

String setimentType = sentence.get(SentimentCoreAnnotations.SentimentClass.class);

sentimentResult.setSentimentType(setimentType);

sentimentResult.setSentimentClass(classification);

sentimentResult.setSentimentScore(RNNCoreAnnotations.getPredictedClass(tree));

}

}

return sentimentResult;

}

}

Sentiment Analysis
Sentiment Analysis

package com.interviewBubble.sentimentanalysis;

public class SentimentAnalysis {

public static void main(String[] args) {

     // I have taken iPhone X (Silver) User Review from Amazon

     String text = "Just love the X. Feel so Premium and a Head turner too. Face ID working fine but still miss "

     + "the fingerprint scanner very much. I jump from 5S to X so it’s a huge skip. I’m very very happy"

     + " with it. Specially battery backup is great after using with 4g cellular network and no heating "

     + "issue at all, though I’m not a mobile gamer, Oftentimes I play Boom Beach and I watch YouTube "

     + "videos and I surf a lot. It makes a deep hole in pocket at the Hefty price tag. So it’s all "

     + "upto your Consideration.n";

     SentimentAnalyzer sentimentAnalyzer = new SentimentAnalyzer();

     sentimentAnalyzer.initialize();

     SentimentResult sentimentResult = sentimentAnalyzer.getSentimentResult(text);

     

     System.out.println("Sentiments Classification:");

System.out.println("Very positive: " + sentimentResult.getSentimentClass().getVeryPositive()+"%");

System.out.println("Positive: " + sentimentResult.getSentimentClass().getPositive()+"%");

System.out.println("Neutral: " + sentimentResult.getSentimentClass().getNeutral()+"%");

System.out.println("Negative: " + sentimentResult.getSentimentClass().getNegative()+"%");

System.out.println("Very negative: " + sentimentResult.getSentimentClass().getVeryNegative()+"%");

     System.out.println("nSentiments result:");

     System.out.println("Sentiment Score: " + sentimentResult.getSentimentScore());

System.out.println("Sentiment Type: " + sentimentResult.getSentimentType());

}

}

Console OUTPUT
Console OUTPUT

0    [main] INFO  edu.stanford.nlp.pipeline.StanfordCoreNLP  - Adding annotator tokenize

8    [main] INFO  edu.stanford.nlp.pipeline.TokenizerAnnotator  - No tokenizer type provided. Defaulting to PTBTokenizer.

12   [main] INFO  edu.stanford.nlp.pipeline.StanfordCoreNLP  - Adding annotator ssplit

17   [main] INFO  edu.stanford.nlp.pipeline.StanfordCoreNLP  - Adding annotator parse

512  [main] INFO  edu.stanford.nlp.parser.common.ParserGrammar  - Loading parser from serialized file edu/stanford/nlp/models/lexparser/englishPCFG.ser.gz ... done [0.5 sec].

517  [main] INFO  edu.stanford.nlp.pipeline.StanfordCoreNLP  - Adding annotator sentiment

Sentiments Classification:

Very positive: 4%

Positive: 23%

Neutral: 24%

Negative: 39%

Very negative: 8%

Sentiments result:

Sentiment Score: 1

Sentiment Type: Negative

pom.xml
pom.xml

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"

  xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">

  <modelVersion>4.0.0</modelVersion>

  <groupId>com.interviewBubble</groupId>

  <artifactId>CoreNLP</artifactId>

  <version>1.0-SNAPSHOT</version>

  <packaging>jar</packaging>

  <name>CoreNLP</name>

  <url>http://maven.apache.org</url>

  <properties>

    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>

    <stanford.corenlp.version>3.9.1</stanford.corenlp.version>

  </properties>

  <dependencies>

    <dependency>

      <groupId>junit</groupId>

      <artifactId>junit</artifactId>

      <version>3.8.1</version>

      <scope>test</scope>

    </dependency>

<!-- Stanford dependecies -->

       <dependency>

           <groupId>edu.stanford.nlp</groupId>

           <artifactId>stanford-corenlp</artifactId>

<version>${stanford.corenlp.version}</version>

<scope>compile</scope>

</dependency>

<dependency>

<groupId>edu.stanford.nlp</groupId>

<artifactId>stanford-corenlp</artifactId>

<classifier>models</classifier>

<version>${stanford.corenlp.version}</version>

<scope>compile</scope>

</dependency>

  <dependency>

     <groupId>org.slf4j</groupId>

       <artifactId>slf4j-api</artifactId>

       <version>1.7.25</version>

   </dependency>

   <dependency>

       <groupId>org.slf4j</groupId>

       <artifactId>slf4j-log4j12</artifactId>

       <version>1.7.25</version>

   </dependency>

  </dependencies>

</project>

Extras: Examples 2

Getting Prediction at Classification Level
Getting Prediction at Classification Level

package com.interviewBubble.sentimentanalysis;

import java.util.Properties;

import org.ejml.simple.SimpleMatrix;

import edu.stanford.nlp.ling.CoreAnnotations;

import edu.stanford.nlp.neural.rnn.RNNCoreAnnotations;

import edu.stanford.nlp.pipeline.Annotation;

import edu.stanford.nlp.pipeline.StanfordCoreNLP;

import edu.stanford.nlp.sentiment.SentimentCoreAnnotations;

import edu.stanford.nlp.trees.Tree;

import edu.stanford.nlp.util.CoreMap;

public class SentimentAnalyzer {

StanfordCoreNLP pipeline;

public void initialize() {

Properties properties = new Properties();

properties.setProperty("annotators", "tokenize, ssplit, parse, sentiment");

pipeline = new StanfordCoreNLP(properties);

}

public SentimentResult getSentimentResult(String text) {

SentimentClassification classification = new SentimentClassification();

SentimentResult sentimentResult = new SentimentResult();

if (text != null && text.length() > 0) {

Annotation annotation = pipeline.process(text);

for(CoreMap sentence: annotation.get(CoreAnnotations.SentencesAnnotation.class)) {

    System.out.println("Sentence: "+ sentence);

Tree tree = sentence.get(SentimentCoreAnnotations.SentimentAnnotatedTree.class);

System.out.println("TREE" + tree);

SimpleMatrix simpleMatrix = RNNCoreAnnotations.getPredictions(tree);

System.out.println("SimpleMatrix" + simpleMatrix);

classification.setVeryNegative((int)Math.round(simpleMatrix.get(0)*100d));

classification.setNegative((int)Math.round(simpleMatrix.get(1)*100d));

classification.setNeutral((int)Math.round(simpleMatrix.get(2)*100d));

classification.setPositive((int)Math.round(simpleMatrix.get(3)*100d));

classification.setVeryPositive((int)Math.round(simpleMatrix.get(4)*100d));

String setimentType = sentence.get(SentimentCoreAnnotations.SentimentClass.class);

sentimentResult.setSentimentType(setimentType);

sentimentResult.setSentimentClass(classification);

sentimentResult.setSentimentScore(RNNCoreAnnotations.getPredictedClass(tree));

}

}

return sentimentResult;

}

}

Console OUTPUT
Console OUTPUT

0    [main] INFO  edu.stanford.nlp.pipeline.StanfordCoreNLP  - Adding annotator tokenize8    [main] INFO  edu.stanford.nlp.pipeline.TokenizerAnnotator  - No tokenizer type provided. Defaulting to PTBTokenizer.13   [main] INFO  edu.stanford.nlp.pipeline.StanfordCoreNLP  - Adding annotator ssplit17   [main] INFO  edu.stanford.nlp.pipeline.StanfordCoreNLP  - Adding annotator parse534  [main] INFO  edu.stanford.nlp.parser.common.ParserGrammar  - Loading parser from serialized file edu/stanford/nlp/models/lexparser/englishPCFG.ser.gz ... done [0.5 sec].540  [main] INFO  edu.stanford.nlp.pipeline.StanfordCoreNLP  - Adding annotator sentimentSentence: Just love the X. Feel so Premium and a Head turner too.TREE(ROOT (ADVP Just) (@S (VP (VB love) (S (@S (S (NP (DT the) (@NP (NNP X.) (NNP Feel))) (ADVP (RB so) (RB Premium))) (CC and)) (S (NP (DT a) (@NP (NNP Head) (NN turner))) (ADVP too)))) (. .)))SimpleMatrixType = dense , numRows = 5 , numCols = 10.033 0.193 0.564 0.184 0.026 Sentence: Face ID working fine but still miss the fingerprint scanner very much.TREE(ROOT (NP (NP (NNP Face) (NNP ID)) (VP (VBG working) (UCP (@UCP (ADJP fine) (CC but)) (ADVP still)))) (@S (VP (@VP (VBP miss) (NP (DT the) (@NP (NN fingerprint) (NN scanner)))) (ADVP (RB very) (RB much))) (. .)))SimpleMatrixType = dense , numRows = 5 , numCols = 10.121 0.654 0.194 0.021 0.010 Sentence: I jump from 5S to X so it’s a huge skip.TREE(ROOT (NP I) (@S (VP (@VP (VBP jump) (PP (IN from) (NP (@QP (CD 5S) (TO to)) (CD X)))) (SBAR (IN so) (S (NP it) (VP (VBZ 's) (NP (DT a) (@NP (JJ huge) (NN skip))))))) (. .)))SimpleMatrixType = dense , numRows = 5 , numCols = 10.258 0.598 0.101 0.028 0.015 Sentence: I’m very very happy with it.TREE(ROOT (NP I) (@S (VP (VBP 'm) (ADJP (ADJP (RB very) (@ADJP (RB very) (JJ happy))) (PP (IN with) (NP it)))) (. .)))SimpleMatrixType = dense , numRows = 5 , numCols = 10.008 0.008 0.025 0.333 0.626 Sentence: Specially battery backup is great after using with 4g cellular network and no heating issue at all, though I’m not a mobile gamer, Oftentimes I play Boom Beach and I watch YouTube videos and I surf a lot.TREE(ROOT (NP (ADJP (RB Specially) (NN battery)) (NN backup)) (@S (VP (VBZ is) (ADJP (JJ great) (PP (IN after) (S (@VP (VBG using) (PP (IN with) (NP (@NP (NP (JJ 4g) (@NP (JJ cellular) (NN network))) (CC and)) (NP (DT no) (@NP (NN heating) (NN issue)))))) (PP (IN at) (S (@S (@S (@S (S (NP (@NP (@NP (NP all) (, ,)) (SBAR (IN though) (S (NP I) (VP (@VP (VBP 'm) (RB not)) (NP (DT a) (@NP (JJ mobile) (NN gamer))))))) (, ,)) (VP (VBZ Oftentimes) (S (NP I) (VP (VB play) (NP (NNP Boom) (NNP Beach)))))) (CC and)) (S (NP I) (VP (VBP watch) (NP (NNP YouTube) (NNS videos))))) (CC and)) (S (NP I) (VP (VBZ surf) (NP (DT a) (NN lot)))))))))) (. .)))SimpleMatrixType = dense , numRows = 5 , numCols = 10.216 0.473 0.166 0.085 0.059 Sentence: It makes a deep hole in pocket at the Hefty price tag.TREE(ROOT (NP It) (@S (VP (@VP (VBZ makes) (NP (NP (DT a) (@NP (JJ deep) (NN hole))) (PP (IN in) (NP pocket)))) (PP (IN at) (NP (DT the) (@NP (NNP Hefty) (@NP (NN price) (NN tag)))))) (. .)))SimpleMatrixType = dense , numRows = 5 , numCols = 10.325 0.531 0.103 0.021 0.020 Sentence: So it’s all upto your Consideration.TREE(ROOT (IN So) (@S (NP it) (@S (VP (@VP (VBZ 's) (RB all)) (VP (VBG upto) (NP (PRP$ your) (NN Consideration)))) (. .))))SimpleMatrixType = dense , numRows = 5 , numCols = 10.085 0.393 0.243 0.235 0.044 Sentiments Classification:Very positive: 4%Positive: 23%Neutral: 24%Negative: 39%Very negative: 8%Sentiments result:Sentiment Score: 1Sentiment Type: Negative

Examples: 3

Sentiment Analysis
Sentiment Analysis

package com.interviewBubble.sentimentanalysis;

import java.util.Properties;

import org.ejml.simple.SimpleMatrix;

import edu.stanford.nlp.ling.CoreAnnotations;

import edu.stanford.nlp.neural.rnn.RNNCoreAnnotations;

import edu.stanford.nlp.pipeline.Annotation;

import edu.stanford.nlp.pipeline.StanfordCoreNLP;

import edu.stanford.nlp.sentiment.SentimentCoreAnnotations;

import edu.stanford.nlp.trees.Tree;

import edu.stanford.nlp.util.CoreMap;

public class SentimentAnalyzer {

StanfordCoreNLP pipeline;

public void initialize() {

Properties properties = new Properties();

properties.setProperty("annotators", "tokenize, ssplit, parse, sentiment");

pipeline = new StanfordCoreNLP(properties);

}

public SentimentResult getSentimentResult(String text) {

SentimentClassification classification = new SentimentClassification();

SentimentResult sentimentResult = new SentimentResult();

if (text != null && text.length() > 0) {

Annotation annotation = pipeline.process(text);

for(CoreMap sentence: annotation.get(CoreAnnotations.SentencesAnnotation.class)) {

    //System.out.println("Sentence: "+ sentence);

Tree tree = sentence.get(SentimentCoreAnnotations.SentimentAnnotatedTree.class);

//System.out.println("TREE" + tree);

SimpleMatrix simpleMatrix = RNNCoreAnnotations.getPredictions(tree);

//System.out.println("SimpleMatrix" + simpleMatrix);

classification.setVeryNegative((int)Math.round(simpleMatrix.get(0)*100d));

classification.setNegative((int)Math.round(simpleMatrix.get(1)*100d));

classification.setNeutral((int)Math.round(simpleMatrix.get(2)*100d));

classification.setPositive((int)Math.round(simpleMatrix.get(3)*100d));

classification.setVeryPositive((int)Math.round(simpleMatrix.get(4)*100d));

String setimentType = sentence.get(SentimentCoreAnnotations.SentimentClass.class);

int sentimentScore =  RNNCoreAnnotations.getPredictedClass(tree);

sentimentResult.setSentimentType(setimentType);

sentimentResult.setSentimentClass(classification);

sentimentResult.setSentimentScore(sentimentScore);

    System.out.println("SentimentScore: " + sentimentScore + ", " + "Sentence: "+ sentence);

}

}

return sentimentResult;

}

}

Console OUTPUT
Console OUTPUT

0    [main] INFO  edu.stanford.nlp.pipeline.StanfordCoreNLP  - Adding annotator tokenize

7    [main] INFO  edu.stanford.nlp.pipeline.TokenizerAnnotator  - No tokenizer type provided. Defaulting to PTBTokenizer.

12   [main] INFO  edu.stanford.nlp.pipeline.StanfordCoreNLP  - Adding annotator ssplit

16   [main] INFO  edu.stanford.nlp.pipeline.StanfordCoreNLP  - Adding annotator parse

525  [main] INFO  edu.stanford.nlp.parser.common.ParserGrammar  - Loading parser from serialized file edu/stanford/nlp/models/lexparser/englishPCFG.ser.gz ... done [0.5 sec].

530  [main] INFO  edu.stanford.nlp.pipeline.StanfordCoreNLP  - Adding annotator sentiment

SentimentScore: 2, Sentence: Just love the X. Feel so Premium and a Head turner too.

SentimentScore: 1, Sentence: Face ID working fine but still miss the fingerprint scanner very much.

SentimentScore: 1, Sentence: I jump from 5S to X so it’s a huge skip.

SentimentScore: 4, Sentence: I’m very very happy with it.

SentimentScore: 1, Sentence: Specially battery backup is great after using with 4g cellular network and no heating issue at all, though I’m not a mobile gamer, Oftentimes I play Boom Beach and I watch YouTube videos and I surf a lot.

SentimentScore: 1, Sentence: It makes a deep hole in pocket at the Hefty price tag.

SentimentScore: 1, Sentence: So it’s all upto your Consideration.

Sentiments Classification:

Very positive: 4%

Positive: 23%

Neutral: 24%

Negative: 39%

Very negative: 8%

Sentiments result:

Sentiment Score: 1

Sentiment Type: Negative