Uzyskaj antonimy słowa w języku java - Wordnet JWI

Dec 22 2020

Jestem zainteresowany znalezieniem antonimów dla słowa przy użyciu wordnet w Javie. Obecnie używam tej metody do znajdowania antonimów, ale nie znalazłem jeszcze żadnych słów, które mają antonimy. Czy antonimy nie są powszechne w Wordnecie? A może ta implementacja jest wadliwa?

public List<String> getAntonyms(String baseWord) {
    List<String> synonymList = new ArrayList<>();
    IIndexWord[] baseWordPOS = getAllPOSForBaseWord(baseWord);
    for (IIndexWord iIndexWord : baseWordPOS) {
        if (iIndexWord == null) {
            continue;
        }
        for (IWordID wordID : iIndexWord.getWordIDs()) {
            IWord word = dict.getWord(wordID);
            ISynset synset = word.getSynset();
            Map<IPointer, List<ISynsetID>> relatedMap = synset.getRelatedMap();
            for (Map.Entry<IPointer, List<ISynsetID>> entry : relatedMap.entrySet()) {
                IPointer iPointer = entry.getKey();
                if (iPointer.equals(Pointer.ANTONYM)) {
                    List<ISynsetID> iSunsetIDS = entry.getValue();
                    for (ISynsetID iSynsetID : iSunsetIDS) {
                        ISynset synset1 = dict.getSynset(iSynsetID);
                        for (IWord w : synset1.getWords()) {
                            synonymList.add(ConvertToPolyFormat(w.getLemma()));
                        }
                    }
                }
            }
        }
    }
    return synonymList.stream()
            .distinct()
            .filter(s -> !s.equals(baseWord))
            .collect(Collectors.toList());
} 

Testuję tymi słowami:

String[] testWords = {"able", "unable", "adsorbent", "apple", "tart", "computer", "cat", "great", "allowable"};

ale wszystkie zwracają puste listy. Sprawdzam wszystkie części mowy (POS) dla słowa:

private static final POS[] POS_ARRAY = {POS.ADJECTIVE, POS.ADVERB, POS.NOUN, POS.VERB};
private IIndexWord[] getAllPOSForBaseWord(String baseWord) {
    IIndexWord[] returnValue = new IIndexWord[4];
    for (int i = 0; i < returnValue.length; i++) {
        returnValue[i] = dict.getIndexWord(baseWord, POS_ARRAY[i]);
    }
    return returnValue;
}

Użyłem tego samego podejścia, aby znaleźć synonimy, ale sprawdziłem, czy typ wskaźnika jest powiązany z / hypernym / etc ... i odniosłem sukces z tą implementacją.

Pozostałe informacje:

dictZmienna jest IDictionary przedmiot z ( edu.mit.jwi.IDictionary)

Odpowiedzi

1 ThuatNguyen Dec 23 2020 at 15:59

Myślę, że się pomyliłeś relatedMap. Zmieniłem twój kod w ten sposób i pomyślnie:

public List<String> getAntonyms(String baseWord) {
    List<String> synonymList = new ArrayList<>();
    IIndexWord[] baseWordPOS = getAllPOSForBaseWord(baseWord);
    for (IIndexWord iIndexWord : baseWordPOS) {
        if (iIndexWord == null) {
            continue;
        }
        for (IWordID wordID : iIndexWord.getWordIDs()) {
            IWord word = dict.getWord(wordID);

            Map<IPointer, List<IWordID>> relatedMap = word.getRelatedMap();
            for (Map.Entry<IPointer, List<IWordID>> entry : relatedMap.entrySet()) {
                IPointer iPointer = entry.getKey();
                if (iPointer.equals(Pointer.ANTONYM)) {
                    List<IWordID> iWordIDs = entry.getValue();
                    for (IWordID iWordID : iWordIDs) {
                        IWord iWord = dict.getWord(iWordID);
                        ISynset synset = iWord.getSynset();
                        for (IWord w : synset.getWords()) {
                            synonymList.add(ConvertToPolyFormat(w.getLemma()));
                        }
                    }
                }
            }
        }
    }
    return synonymList.stream()
            .distinct()
            .filter(s -> !s.equals(baseWord))
            .collect(Collectors.toList());
}