Java отрицательный indexOf (отсчет от конца [длина()])

есть ли способ в Java найти indexOf символа, начинающегося с конца и имеющего length() в качестве ссылки, как это делают другие языки?

   new String("abcd").reverseIndexOf("d"(,[4 or -0]))
or new String("abcd").indexOf("d",-0) // Should return a (-)1

...вместо очевидного

   new String("abcd").indexOf("d") - newString("abcd").length()     

спасибо!

3 ответов


lastIndexOf(int ch) будет начинаться с конца и искать назад, возвращая абсолютный индекс последнего вхождения. Тогда вы можете вычесть это число из длины строки и отрицать его, если это то, что вы действительно хотите.

вы также можете использовать lastIndexOf(int ch, int fromIndex)если вы хотите искать назад от определенного индекса.

чтобы ответить на ваш вопрос о том, что происходит, когда вы передать отрицательное число, вы можете покопаться в исходном коде для класса String. Как оказалось,indexOf реализация, которая в конечном итоге называется сбрасывает отрицательный fromIndex значения до нуля:

static int indexOf(char[] source, int sourceOffset, int sourceCount,
                   char[] target, int targetOffset, int targetCount,
                   int fromIndex) {
if (fromIndex >= sourceCount) {
        return (targetCount == 0 ? sourceCount : -1);
}
    if (fromIndex < 0) {
        fromIndex = 0;
    }
    ...

возвращаясь ко второму примеру:

"abcd".indexOf("d",-0)

...реализация универсального indexOf, который принимает отрицательный индекс и возвращает соответствующий отрицательный индекс (если он есть), сложнее, потому что Java не различает int 0 и int -0 (оба будут представлены как 0), и потому что стринг.indexOf обычно возвращает -1, если строка поиска не найдена. Однако вы можете приблизиться к тому, чего хотите. Обратите внимание, что есть несколько предостережений:

  1. String.indexOf возвращается -1 если строка поиска не найдена. Но потому что -1 является действительным индексом в нашей новой реализации, нам нужно определить новый контракт. Integer.MIN_VALUE теперь возвращается, если строка поиска не найдена.
  2. потому что мы не можем проверить для int -0, мы не можем обратитесь к индексу последнего символа как -0. По этой причине, мы используем -1 чтобы обратиться к индексу последнего символа и продолжить отсчет назад оттуда.
  3. для согласованности с пунктом 2 отрицательные возвращаемые значения также начинают обратный отсчет, начиная с -1 как индекс последнего символа.

код может быть упрощен, но я намеренно сделал его подробным, чтобы вы могли легко пройти через него в отладчик.

package com.example.string;

public class StringExample {

    public static int indexOf(String str, String search, int fromIndex) {
        if (fromIndex < 0) {
            fromIndex = str.length() + fromIndex; // convert the negative index to a positive index, treating the negative index -1 as the index of the last character
            int index = str.lastIndexOf(search, fromIndex);
            if (index == -1) {
                index = Integer.MIN_VALUE; // String.indexOf normally returns -1 if the character is not found, but we need to define a new contract since -1 is a valid index for our new implementation
            }
            else {
                index = -(str.length() - index); // convert the result to a negative index--again, -1 is the index of the last character 
            }
            return index;
        }
        else {
            return str.indexOf(str, fromIndex);
        }
    }

    public static void main(String[] args) {
        System.out.println(indexOf("abcd", "d", -1)); // returns -1
        System.out.println(indexOf("adbcd", "d", -2)); // returns -4
    }
}

просто использовать String.lastIndexOf() способ:

String s = "abcd";
int rindex = s.lastIndexof('d');
System.out.println(rindex); // print 0

вы можете легко изменить строку, кстати:

String s="abcd";
StringBuilder reverseS = new StringBuilder(s).reverse();
System.out.println(reverseS.indexOf("d")); //print 0
System.out.println(reverseS.indexOf("a")); //print 3
System.out.println(reverseS.indexOf("d",1)); //print -1