基於LingPipe的文本基本極性分析【demo】


酒店評論情感分析系統(四)——

基於LingPipe的文本基本極性分析【demo】

(Positive (favorable) vs. Negative (unfavorable))

這篇文章為LingPipe官方網站對於Sentiment Ananlysis的學習所給出學習材料;

http://alias-i.com/lingpipe/demos/tutorial/sentiment/read-me.html

官方網站中的學習材料是通過使用邏輯回歸分類器基於一定的語言模型對電影評論賦予一定的情感,其中包括兩種常見的情感分類問題:

a)      主觀性和客觀性情感分析

b)      積極性和消極性情感分析

但是此處,我只學習了積極性和消極性情感分析。

下載語料庫

此處使用Lilian Lee 和Bo Pang提供的已經完成了極性標注的電影評論語料庫Movie Review Data的polarity dataset v2.0,其中包含1000個正面的文本和1000個負面文本,全英文的。運用POLARITY_DIR目錄去放置解壓過的評論語料庫。

基本極性分析

我們以一個簡單的分類練習作為開始,即基於布爾極性數據來訓練和測試基本分類器,並使產生的分類器能夠判斷電影評論實質上是積極的或是消極的。

官方網站上的demo是通過命令行的形式讀入語料庫所在的目錄位置,然后基於訓練集訓練出一個分類器,再基於測試集評估此分類器的正確性。此處我將其變更為以文件的形式讀取語料庫所在的位置。

1.      前提條件:

1)  在Eclipse中新建一個名為SentimentAnalysis工程,配置LingPipe開源包

2)  在SentimentAnalysis工程下創建一個目錄POLARITY_DIR,里面放置語料庫polarity dataset v2.0的解壓縮文件txt_sentoken。

2.      極性分析代碼

新建一個類名為PolarityBasic。

①   Main函數

1 public static void main(String[] args) {
2 try {
3 new PolarityBasic().run();
4 } catch (Throwable t) {
5 System.out.println("Thrown: " + t);
6 t.printStackTrace(System.out);
7 }
8 }

 

②   元參數和構造函數

 1     File mPolarityDir;
2 String[] mCategories;
3 DynamicLMClassifier<NGramProcessLM> mClassifier;
4
5 PolarityBasic() {
6 System.out.println("\nBASIC POLARITY DEMO");
7 mPolarityDir = new File("POLARITY_DIR/txt_sentoken"); //獲取POLARITY_DIR/txt_sentoken中的語料集
8 mCategories = mPolarityDir.list(); //獲取類別neg,pos
9 int nGram = 8;
10 mClassifier = DynamicLMClassifier.createNGramProcess(mCategories,nGram); //使用N-Gram分類方法
11 }

基本極性分析中分類器的構造直接使用的是LingPipe的DynamicLMClassifier。

③   訓練

 1     //僅僅先調用訓練函數,再調用評估函數
2 void run() throws ClassNotFoundException, IOException {
3 train();
4 evaluate();
5 }
6
7 //我們需要一份測試集和一個訓練集,但是我們只有一個語料庫,只有人為分割
8 //如果文件名的第2位為9就是訓練集
9 boolean isTrainingFile(File file) { //是否是訓練集
10 return file.getName().charAt(2) != '9'; // test on fold 9
11 }
12
13 //分類器訓練
14 void train() throws IOException {
15 int numTrainingCases = 0; //訓練文本數
16 int numTrainingChars = 0; //訓練字符數
17 System.out.println("\nTraining.");
18 for (int i = 0; i < mCategories.length; ++i) {
19 String category = mCategories[i];
20 Classification classification = new Classification(category);
21 File file = new File(mPolarityDir,mCategories[i]);
22 File[] trainFiles = file.listFiles();
23 for (int j = 0; j < trainFiles.length; ++j) {
24 File trainFile = trainFiles[j];
25 if (isTrainingFile(trainFile)) { //判斷一下是為了讓一部分數據作為訓練集、一部分作為測試集
26 ++numTrainingCases;
27 String review = Files.readFromFile(trainFile,"ISO-8859-1"); //文本類容
28 numTrainingChars += review.length();
29 Classified<CharSequence> classified =
30 new Classified<CharSequence>(review,classification); //指定內容和類別
31 mClassifier.handle(classified); //訓練
32 }
33 }
34 }
35 System.out.println(" # Training Cases=" + numTrainingCases); //訓練集文件數
36 System.out.println(" # Training Chars=" + numTrainingChars); //訓練集字符總和
37 }

 

④   評估

 1     //評估
2 void evaluate() throws IOException {
3 System.out.println("\nEvaluating.");
4 int numTests = 0;
5 int numCorrect = 0;
6 for (int i = 0; i < mCategories.length; ++i) {
7 String category = mCategories[i];
8 File file = new File(mPolarityDir,mCategories[i]);
9 File[] trainFiles = file.listFiles();
10 for (int j = 0; j < trainFiles.length; ++j) {
11 File trainFile = trainFiles[j];
12 if (!isTrainingFile(trainFile)) { //測試集
13 String review = Files.readFromFile(trainFile,"ISO-8859-1");
14 ++numTests;
15 Classification classification = mClassifier.classify(review); //對測試集文本進行分類
16 if (classification.bestCategory().equals(category)){ //分類器決策文本所屬類=文本原標注所屬類,即正確
17 ++numCorrect;
18 }
19 }
20 }
21 }
22 System.out.println(" # Test Cases=" + numTests); //測試文件數
23 System.out.println(" # Correct=" + numCorrect); //正確數
24 System.out.println(" % Correct=" + ((double)numCorrect)/(double)numTests); //正確率
25 }

 

⑤    運行結果

BASIC POLARITY DEMO

Training.
# Training Cases=1800
# Training Chars=6989652

Evaluating.
# Test Cases=200
# Correct=163
% Correct=0.815

注意!

本站转载的文章为个人学习借鉴使用,本站对版权不负任何法律责任。如果侵犯了您的隐私权益,请联系我们删除。



 
粤ICP备14056181号  © 2014-2020 ITdaan.com