TheAlgorithms/Java · error · WordsToNumberException

INVALID_NEGATIVE

INVALID_NEGATIVE

Error message

Invalid Input. Incorrect 'negative' placement

What it means

Thrown by handleNegative when the word 'negative' appears anywhere other than the start. Because the parser only strips a leading 'negative' (setting isNegative=true and polling it), any subsequent 'negative' reaches handleNegative with isNegative=false, triggering INVALID_NEGATIVE. This means 'negative' is only legal as the very first token.

Source

Thrown at src/main/java/com/thealgorithms/conversions/WordsToNumber.java:198

        }
        return currentChunk.add(bigDecimalNumber);
    }

    private static void handlePoint(Collection<BigDecimal> chunks, BigDecimal currentChunk, ArrayDeque<String> wordDeque) {
        boolean currentChunkIsZero = currentChunk.compareTo(BigDecimal.ZERO) == 0;
        if (!currentChunkIsZero) {
            chunks.add(currentChunk);
        }

        String decimalPart = convertDecimalPart(wordDeque);
        chunks.add(new BigDecimal(decimalPart));
    }

    private static void handleNegative(boolean isNegative) {
        if (isNegative) {
            throw new WordsToNumberException(WordsToNumberException.ErrorType.MULTIPLE_NEGATIVES, "");
        }
        throw new WordsToNumberException(WordsToNumberException.ErrorType.INVALID_NEGATIVE, "");
    }

    private static BigDecimal convertWordQueueToBigDecimal(ArrayDeque<String> wordDeque) {
        BigDecimal currentChunk = BigDecimal.ZERO;
        List<BigDecimal> chunks = new ArrayList<>();

        boolean isNegative = "negative".equals(wordDeque.peek());
        if (isNegative) {
            wordDeque.poll();
        }

        boolean prevNumWasHundred = false;
        boolean prevNumWasPowerOfTen = false;

        while (!wordDeque.isEmpty()) {
            String word = wordDeque.poll();

            switch (word) {

View on GitHub (pinned to fdfb9a395b)

Solutions

  1. Move 'negative' to the absolute beginning of the phrase.
  2. Validate that if 'negative' is present, it is the first token and appears only once.
  3. Reject inputs where 'negative' appears after position 0.

Example fix

// before
WordsToNumber.convert('five negative');
// after
WordsToNumber.convert('negative five'); // -5
Defensive patterns

Strategy: validation

Validate before calling

static String sanitizeNegative(String s) {
    String[] words = s.trim().toLowerCase(Locale.ROOT).split("[ ,-]+");
    for (int i = 1; i < words.length; i++) {
        if ("negative".equals(words[i])) throw new IllegalArgumentException("'negative' only allowed at start");
    }
    return s;
}

Try / catch

try { WordsToNumber.convert(input); } catch (WordsToNumberException e) {
    if (e.errorType == ErrorType.INVALID_NEGATIVE) throw new ApiException(400, "'negative' must be the first word");
    throw e;
}

Prevention

When it happens

Trigger: convert('five negative'), convert('one hundred negative five'), convert('point five negative'). Any 'negative' that is not the first word.

Common situations: Users placing 'negative' after the number or mid-phrase; expecting per-component negation; LLM output with misplaced negation.

Related errors


AI-assisted analysis of TheAlgorithms/Java@fdfb9a395b (2026-08-13). Data as JSON: /api/errors/84dbf663020557b5. Report an issue: GitHub.