テキスト統計を計算し、その後EDTのGUI要素を結果で更新する仕事をスイングワーカーに書いたことがあります。 実験したところ、ではなく、done()
メソッドでのみGUIを操作する必要があることが分かりました。これを達成するために、戻り値String[]
を改装しました。これはget()
で取得できるはずです。 publish()
のメソッドを除いて、doInBackground()
メソッドから直接GUIを操作している間に悪質な呼び出しがあり、その問題が原因で発生していると思われる場合は、教えてください。 SwingWorker done()メソッドは、get()でnullpointerexceptionをスローします
package my.worker;
import java.math.BigDecimal;
import java.math.RoundingMode;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.TreeSet;
import java.util.concurrent.ExecutionException;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.swing.JComboBox;
import javax.swing.JLabel;
import javax.swing.JProgressBar;
import javax.swing.SwingWorker;
import my.tools.CountKeywords;
import my.tools.FilterStopwords;
import my.tools.KeywordSuggestion;
import my.tools.RelevanceRanking;
public class ProcessDatabaseWorker extends SwingWorker<String[], String> {
private final JLabel debugJLabel;
private final JLabel infoJLabel;
private final JLabel warnJLabel;
private final JLabel errorJLabel;
private final JLabel infoboxJLabel;
private final String databaseString;
private final JProgressBar jProgressBar;
private final JComboBox keywordJComboBox;
private int percent;
private int index;
public ProcessDatabaseWorker(JProgressBar jProgressBar, String databaseString,
JLabel debugJLabel, JLabel errorJLabel, JLabel warnJLabel,
JLabel infoJLabel, JLabel infoboxJLabel,
JComboBox keywordJComboBox) {
this.percent = 1;
this.jProgressBar = jProgressBar;
this.databaseString = databaseString;
this.debugJLabel = debugJLabel;
this.errorJLabel = errorJLabel;
this.infoJLabel = infoJLabel;
this.warnJLabel = warnJLabel;
this.infoboxJLabel = infoboxJLabel;
this.keywordJComboBox = keywordJComboBox;
}
@Override
protected String[] doInBackground() throws Exception {
FilterStopwords fs = new FilterStopwords();
CountKeywords ck = new CountKeywords();
RelevanceRanking rr = new RelevanceRanking();
HashMap<String, Integer> nKeywords = new HashMap();
Map<String, TreeSet<Map.Entry<String, Double>>> keywordsPerDocument = new HashMap();
String replace = databaseString.toLowerCase();
String splitter = ("\\n");
String[] documentLines = replace.split(splitter);
int N = documentLines.length;
publish("Stopworte werden gefiltert...", "10");
String[] completeFilteredText = fs.filterStopwords(replace);
publish("Keywords werden gezählt...", "20");
HashMap<String, Integer> completeKeywords = ck.countKeywords(completeFilteredText);
index = 0;
percent = 1;
final double oneLinePercent = N/100;
final double oneKeywordPercent = completeKeywords.size()/100;
completeKeywords.forEach((String key, Integer value) -> {
int n = 0;
key = String.valueOf(key).trim();
for (String line : documentLines) {
String[] lineWords = line.split(" ");
for (String word : lineWords) {
word = word.trim();
if (word.equals(key)) {
n++;
nKeywords.put(key, n);
}
}
}
index++;
if (index == oneKeywordPercent) {
percent++;
publish("Zählung...", String.valueOf(percent));
index = 0;
}
});
publish("Keywords werden geranked...", "40");
index = 0;
percent = 1;
for (String documentLine : documentLines) {
TreeSet<Map.Entry<String, Double>> rankedKeywords;
String[] lineFilteredWords = fs.filterStopwords(documentLine);
HashMap<String, Integer> keywords = ck.countKeywords(lineFilteredWords);
rankedKeywords = rr.rankKeywords(keywords, lineFilteredWords, N, nKeywords);
keywordsPerDocument.put(documentLine, rankedKeywords);
index++;
if (index == oneLinePercent) {
percent++;
publish("Ranking...", String.valueOf(percent));
index = 0;
}
}
publish("Keyword-Vorschläge werden generiert...", "70");
KeywordSuggestion ks = new KeywordSuggestion();
TreeSet<Map.Entry<String, Double>> keywordSuggestionsTree = ks.keywordSuggestion(keywordsPerDocument);
String[] keywordSuggestionsArray = new String[keywordSuggestionsTree.size()];
index = 0;
int index2 = 0;
double onePercent = keywordSuggestionsTree.size()/100;
percent = 1;
publish("Keyword-Vorschläge werden generiert...", "75");
for (Map.Entry<String, Double> entry : keywordSuggestionsTree) {
double round = round(entry.getValue(), 2);
keywordSuggestionsArray[index2] = round + " - " + entry.getKey();
index2++;
index++;
if (index == onePercent) {
percent++;
publish("Keywords...", String.valueOf(percent));
index = 0;
}
}
keywordJComboBox.removeAllItems();
for (String entry : keywordSuggestionsArray) {
publish("Keyword-Vorschläge werden befüllt...", "80");
}
この
は...ここ return keywordSuggestionsArray;
}
public static double round(double value, int places) {
if (places < 0) {
throw new IllegalArgumentException();
}
BigDecimal bd = new BigDecimal(value);
bd = bd.setScale(places, RoundingMode.HALF_UP);
return bd.doubleValue();
}
@Override
public void process(List<String> s) {
infoboxJLabel.setText(s.get(0));
jProgressBar.setValue(Integer.valueOf(s.get(1)));
}
@Override
protected void done() {
try {
は、NullPointerExceptionがスローされたポイントです...私は、get()のために必要な値を返す行である
String[] get = get();
for (String entry : get) {
keywordJComboBox.addItem(entry);
}
} catch (InterruptedException | ExecutionException ex) {
Logger.getLogger(ProcessDatabaseWorker.class.getName()).log(Level.SEVERE, null, ex);
}
publish("Verarbeitung der Daten abgeschlossen!", "100");
}
}
詳細については、完全なトレースがここにあります:
Apr 14, 2016 10:40:06 AM my.worker.ProcessDatabaseWorker done
SCHWERWIEGEND: null
java.util.concurrent.ExecutionException: java.lang.NullPointerException
at java.util.concurrent.FutureTask.report(FutureTask.java:122)
at java.util.concurrent.FutureTask.get(FutureTask.java:192)
at javax.swing.SwingWorker.get(SwingWorker.java:602)
at my.worker.ProcessDatabaseWorker.done(ProcessDatabaseWorker.java:197)
at javax.swing.SwingWorker$5.run(SwingWorker.java:737)
at javax.swing.SwingWorker$DoSubmitAccumulativeRunnable.run(SwingWorker.java:832)
at sun.swing.AccumulativeRunnable.run(AccumulativeRunnable.java:112)
at javax.swing.SwingWorker$DoSubmitAccumulativeRunnable.actionPerformed(SwingWorker.java:842)
at javax.swing.Timer.fireActionPerformed(Timer.java:313)
at javax.swing.Timer$DoPostEvent.run(Timer.java:245)
at java.awt.event.InvocationEvent.dispatch(InvocationEvent.java:311)
at java.awt.EventQueue.dispatchEventImpl(EventQueue.java:756)
at java.awt.EventQueue.access$500(EventQueue.java:97)
at java.awt.EventQueue$3.run(EventQueue.java:709)
at java.awt.EventQueue$3.run(EventQueue.java:703)
at java.security.AccessController.doPrivileged(Native Method)
at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:76)
at java.awt.EventQueue.dispatchEvent(EventQueue.java:726)
at java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:201)
at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:116)
at java.awt.EventDispatchThread.pumpEventsForHierarchy(EventDispatchThread.java:105)
at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:101)
at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:93)
at java.awt.EventDispatchThread.run(EventDispatchThread.java:82)
Caused by: java.lang.NullPointerException
at my.logfileanalyzer.LogFileAnalyzerGUI.keywordJComboBoxItemStateChanged(LogFileAnalyzerGUI.java:830)
at my.logfileanalyzer.LogFileAnalyzerGUI.access$2400(LogFileAnalyzerGUI.java:48)
at my.logfileanalyzer.LogFileAnalyzerGUI$15.itemStateChanged(LogFileAnalyzerGUI.java:329)
at javax.swing.JComboBox.fireItemStateChanged(JComboBox.java:1223)
at javax.swing.JComboBox.selectedItemChanged(JComboBox.java:1271)
at javax.swing.JComboBox.contentsChanged(JComboBox.java:1330)
at javax.swing.JComboBox.intervalRemoved(JComboBox.java:1352)
at javax.swing.AbstractListModel.fireIntervalRemoved(AbstractListModel.java:179)
at javax.swing.DefaultComboBoxModel.removeAllElements(DefaultComboBoxModel.java:174)
at javax.swing.JComboBox.removeAllItems(JComboBox.java:771)
at my.worker.ProcessDatabaseWorker.doInBackground(ProcessDatabaseWorker.java:165)
at my.worker.ProcessDatabaseWorker.doInBackground(ProcessDatabaseWorker.java:43)
at javax.swing.SwingWorker$1.call(SwingWorker.java:295)
at java.util.concurrent.FutureTask.run(FutureTask.java:266)
at javax.swing.SwingWorker.run(SwingWorker.java:334)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
at java.lang.Thread.run(Thread.java:745)
私の質問のために、ワーカーのどの部分が正しく使用されなかったのですか、あるいは私のプログラムロジックにどこが間違っていましたか?あなたが見ることができるように、私はスイングワーカーとスレッドで一般的にプログラミングするのはかなり新しいので、経験不足による簡単なミスのための簡単な解決策があると確信しています。
また、私のプログラムの他の部分が必要な場合は、何が起こっているかについてより良い画像を描くために、私に教えてください。
EDIT:ユーザーモース-おやおやは説明どこにエラーが正確だった - それを固定し、次のように私のコードを編集した:
private void keywordJComboBoxItemStateChanged(java.awt.event.ItemEvent evt) {
if (keywordJComboBox.getItemCount() != 0){
if (!((String) keywordJComboBox.getSelectedItem()).equals("")) {
String selected = (String) keywordJComboBox.getSelectedItem();
String[] blubb = selected.split(" ");
searchJTextField.setText(blubb[2]);
}
}
}
EDIT:が重複する可能性についてはを - 私はこのポストであることをかなり確信しています。私は正直なところ、swing workers
の実装が間違っていると思っていましたが、実際には単純なものではありませんでした。この投稿は閉鎖されるかもしれません^^
ComboBoxのitemStateChangedでSwingWorkerを起動しますか?もしそうなら、その部分を投稿してください。 –
編集内容をそのまま削除することができます。代わりに 'LogFileAnalyzerGUI'クラスの' keywordJComboBoxItemStateChanged() 'メソッドを投稿してください。 –