in languagetool-language-modules/ca/src/main/java/org/languagetool/rules/ca/ConvertToGenderAndNumberFilter.java [47:230]
public RuleMatch acceptRuleMatch(RuleMatch match, Map<String, String> arguments, int patternTokenPos,
AnalyzedTokenReadings[] patternTokens, List<Integer> tokenPositions) throws IOException {
AnalyzedTokenReadings[] tokens = match.getSentence().getTokensWithoutWhitespace();
Synthesizer synth = getSynthesizerFromRuleMatch(match);
int posWord = 0;
while (posWord < tokens.length
&& (tokens[posWord].getStartPos() < match.getFromPos() || tokens[posWord].isSentenceStart())) {
posWord++;
}
String desiredGenderStr = getOptional("gender", arguments, "");
String desiredNumberStr = getOptional("number", arguments, "");
String lemmaSelect = getRequired("lemmaSelect", arguments);
String newLemma = getOptional("newLemma", arguments, "");
boolean keepOriginal = getOptional("keepOriginal", arguments, "false").equalsIgnoreCase("true");
AnalyzedToken atrNoun = tokens[posWord].readingWithTagRegex(lemmaSelect);
String[] splitPostag = splitGenderAndNumber(atrNoun);
if (desiredGenderStr.isEmpty()) {
desiredGenderStr = splitPostag[2];
}
if (desiredNumberStr.isEmpty()) {
desiredNumberStr = splitPostag[3];
}
if (!newLemma.isEmpty()) {
atrNoun = new AnalyzedToken(atrNoun.getToken(), atrNoun.getPOSTag(), newLemma);
}
int startPos = posWord;
int endPos = posWord;
List<String> suggestions = new ArrayList<>();
for (char genderCh : desiredGenderStr.toCharArray()) {
for (char numberCh : desiredNumberStr.toCharArray()) {
String desiredGender = String.valueOf(genderCh);
String desiredNumber = String.valueOf(numberCh);
StringBuilder suggestionBuilder = new StringBuilder();
boolean ignoreThisSuggestion = false;
if (!keepOriginal) {
String s = synthesizeWithGenderAndNumber(atrNoun, splitPostag, desiredGender, desiredNumber, synth);
if (s.isEmpty()) {
ignoreThisSuggestion=true;
}
suggestionBuilder.append(s);
} else {
suggestionBuilder.append(atrNoun.getToken());
}
//backwards
boolean stop = false;
int i = posWord;
String prepositionToAdd = "";
boolean addDeterminer = false;
boolean addedDemostrative = false;
StringBuilder conditionalAddedString = new StringBuilder();
String addTot = "";
while (!stop && i > 1) {
i--;
AnalyzedToken atr = tokens[i].readingWithTagRegex(splitGenderNumberNoNoun); //getReadingWithPriority(tokens[i]);
if (tokens[i].hasPosTag("_perfet") || tokens[i].hasPosTag("_GV_") || tokens[i].getChunkTags().contains(new ChunkTag("GV"))) {
atr = null;
}
if (atr != null) {
if (atr.getPOSTag().startsWith("DA")) {
addDeterminer = true;
startPos = i;
} else {
if (!addDeterminer && !addedDemostrative) {
String s = synthesizeWithGenderAndNumber(atr, splitGenderAndNumber(atr), desiredGender, desiredNumber, synth);
if (s.isEmpty()) {
ignoreThisSuggestion=true;
}
if (s.equals("bo")) {
s = "bon";
}
suggestionBuilder.insert(0, conditionalAddedString);
conditionalAddedString.setLength(0);
if (tokens[i+1].isWhitespaceBefore()) {
suggestionBuilder.insert(0, " ");
}
suggestionBuilder.insert(0, s);
startPos = i;
if (atr.getPOSTag().startsWith("DD")) {
addedDemostrative = true;
}
if (atr.getPOSTag().startsWith("D") && !atr.getPOSTag().startsWith("DN") && !addedDemostrative) {
stop = true;
}
} else {
// only before "el/aquest/aquell...": tota l'estona, tota aquella estona
if (atr.getLemma().equals("tot")) {
String s = synthesizeWithGenderAndNumber(atr, splitGenderAndNumber(atr), desiredGender, desiredNumber, synth);
if (!s.isEmpty()) {
addTot = s + " ";
startPos = i;
}
}
stop = true;
}
}
} else if (tokens[i].hasPosTag("SPS00") || tokens[i].hasPosTag("LOC_PREP")) {
if (addDeterminer) {
String preposition = tokens[i].getToken().toLowerCase();
if (preposition.equals("pe")) {
preposition = "per";
}
if (preposition.equals("d'")) {
preposition = "de";
}
if (preposition.equals("a") || preposition.equals("de") || preposition.equals("per")) {
prepositionToAdd = preposition;
startPos = i;
}
}
stop = true;
} else if (tokens[i].hasPosTag("_PUNCT_CONT") || tokens[i].hasPosTag("CC")) {
if (posWord - i == 1) {
stop = true;
} else {
conditionalAddedString.insert(0, tokens[i].getToken() + " ");
}
} else if (tokens[i].hasPosTag("RG")) {
conditionalAddedString.insert(0, tokens[i].getToken() + " ");
} else {
stop = true;
}
}
// forwards
stop = false;
i = posWord;
conditionalAddedString.setLength(0);
boolean isThereConjunction = false;
while (!stop && i < tokens.length - 1) {
i++;
AnalyzedToken atr = tokens[i].readingWithTagRegex(splitGenderNumberAdjective);
if (isThereConjunction && tokens[i].hasPosTagStartingWith("NC")) {
atr = null;
}
if (atr != null) {
String s = synthesizeWithGenderAndNumber(atr, splitGenderAndNumber(atr), desiredGender, desiredNumber, synth);
if (s.isEmpty()) {
ignoreThisSuggestion=true;
}
suggestionBuilder.append(conditionalAddedString);
conditionalAddedString.setLength(0);
suggestionBuilder.append(" " + s);
endPos = i;
} else if (tokens[i].hasPosTag("RG")) {
conditionalAddedString.append(" " + tokens[i].getToken());
} else if (tokens[i].hasPosTag("CC")) {
isThereConjunction = true;
conditionalAddedString.append(" " + tokens[i].getToken());
}else if (tokens[i].hasPosTag("_PUNCT_CONT")) {
conditionalAddedString.append(tokens[i].getToken());
} else {
stop = true;
}
}
if (addDeterminer) {
suggestionBuilder.insert(0, getPrepositionAndDeterminer(suggestionBuilder.toString(), desiredGender + desiredNumber, prepositionToAdd));
} else if (!prepositionToAdd.isEmpty()) {
suggestionBuilder.insert(0, prepositionToAdd + " ");
}
suggestionBuilder.insert(0, addTot);
String suggestion = StringTools.preserveCase(suggestionBuilder.toString(), tokens[startPos].getToken());
if (endPos == posWord && startPos == posWord && tokens[posWord].getToken().equals(suggestion)) {
continue;
}
//TODO: una d'aquests vessants; una dels vessants
if (!ignoreThisSuggestion) {
suggestions.add(suggestion);
}
}
}
if (suggestions.isEmpty()) {
return null;
}
RuleMatch ruleMatch = new RuleMatch(match.getRule(), match.getSentence(), tokens[startPos].getStartPos(),
tokens[endPos].getEndPos(), match.getMessage(), match.getShortMessage());
String originalStr = match.getSentence().getText().substring(tokens[startPos].getStartPos(), tokens[endPos].getEndPos());
if (suggestions.contains(originalStr)) {
return null;
}
ruleMatch.setType(match.getType());
ruleMatch.setSuggestedReplacements(suggestions);
return ruleMatch;
}