Просто интересно, знал ли кто-нибудь в голову, есть ли большая разница в том, чтобы сделать следующее:
String wibble = "<blah> blah blah </blah>.... <wibble> blah wibble blah </wibble> some more test here";
int i = wibble.lastIndexOf(">");
int j = wibble.lastIndexOf('>');




С точки зрения производительности может быть небольшая разница. Для поиска одного символа быстрее или равнозначнее использовать char вместо String.
У строки есть дополнительные накладные расходы, которые требуются независимо от ее длины (если у вас нет действительно умного компилятора, который все равно оптимизирует односимвольные строковые литералы в символьные константы :)), поэтому вам следует предпочесть версию char, если вы ищете только одиночные символы. Это не плохая оптимизация, поскольку в любом случае она читаемо эквивалентна.
Вы действительно можете посмотреть исходный код класса String. Кажется, что lastIndex (char) и lastIndex (String) были написаны отдельно. Также должны быть накладные расходы с классом String. Таким образом, версия char может быть немного быстрее, но я сомневаюсь, что будет случай с какой-либо значительной разницей в производительности.
Там, где нет разницы в удобочитаемости (как в этом случае), лучше выбрать версию, которая ищет только символ. У lastIndexOf меньше работы - проще найти один элемент в списке, чем найти подсписок (что, по сути, и делает поиск строки).
Ключевым моментом здесь является удобочитаемость. Неприемлемым микрооптом, на мой взгляд, был бы if (needle.length() == 1) { i = haystack.lastIndexOf(needle.charAt[0]); } else {....
может быть (по общему признанию слабый) аргумент для использования строковой версии для удобства обслуживания, если строка поиска может быть длиной более одного символа в будущем, т. е. меньше усилий переходить с ">" на "/>", если подобное изменение необходимо.
@ Кип: Это достаточно легко изменить, когда вам это нужно, ИМО.
Мнения отличные, но данные лучше. Я написал быстрый тест:
public static void main(String[] args)
{
System.out.println("Starting perfo test");
final long NUM_TESTS = 100000000L;
String wibble = "<blah> blah blah </blah>.... <wibble>"
+ " blah wibble blah </wibble> some more test here";
int x = -1;
Stopwatch sw = new Stopwatch();
System.out.println("--perfo test with " + NUM_TESTS + " iterations--");
sw.start();
for(long i = 0; i < NUM_TESTS; i++)
x = wibble.lastIndexOf(">");
sw.stop();
System.out.println("String first pass: " + sw + " seconds");
sw.start();
for(long i = 0; i < NUM_TESTS; i++)
x = wibble.lastIndexOf('>');
sw.stop();
System.out.println("Char first pass: " + sw + " seconds");
sw.start();
for(long i = 0; i < NUM_TESTS; i++)
x = wibble.lastIndexOf('>');
sw.stop();
System.out.println("Char second pass: " + sw + " seconds");
sw.start();
for(long i = 0; i < NUM_TESTS; i++)
x = wibble.lastIndexOf(">");
sw.stop();
System.out.println("String second pass: " + sw + " seconds");
//Compiler warning said x was never read locally.. this is to
//ensure the compiler doesn't optimize "x" away..
System.out.println(x);
}
Starting perfo test --perfo test with 100000000 iterations-- String first pass: 8.750 seconds Char first pass: 6.500 seconds Char second pass: 6.437 seconds String second pass: 8.610 seconds 63
Версия с символом примерно на 25% быстрее, но обе версии выполняются очень быстро, поэтому она, вероятно, никогда не станет узким местом в вашем коде.
Не беспокойтесь об этом, это не будет иметь большого значения. Выберите тот, который более понятен