Вы также можете использовать подходящий инструмент: Integer.toString(int)
: это может быть проще для чтения, поскольку оно ясно показывает ваше намерение получить String
из вашего int
.
int privacyLevel = 0;
builder.addFormDataPart("privacy", Integer.toString(privacyLevel));
Когда вы используете:
builder.addFormDataPart("privacy", "" + privacyLevel);
Вы создаете новую строку из ""
и Integer.toString(privacyLevel)
, но возможна некоторая оптимизация во время компиляции или во время выполнения:
- Компилятор может обнаружить
""
и напрямую использовать Integer.toString(privacyLevel)
. - Компилятор может заменить операцию
+
методом String::concat
. Указанный метод может вернуть другой String
, если сам по себе пуст, или вернуть себя, когда other String
пуст (в openjdk 8u232 метод фактически проверяет длину other и всегда выполняйте конкатенацию).
Теперь, чтобы увидеть, что делает компилятор, вот простой код, который ничего необычного не делает:
class Foobar {
public static void main(String[] args) {
int n = 1;
String s = n + "";
}
}
Если вы вызываете javap -p Foobar.class
, вы можете увидеть, что сделал компилятор (с Java 11.0.6, Java 8 используйте StringBuilder
):
public static void main(java.lang.String[]);
descriptor: ([Ljava/lang/String;)V
flags: (0x0009) ACC_PUBLIC, ACC_STATIC
Code:
stack=1, locals=3, args_size=1
0: iconst_1
1: istore_1
2: iload_1
3: invokedynamic #2, 0 // InvokeDynamic #0:makeConcatWithConstants:(I)Ljava/lang/String;
8: astore_2
9: return
LineNumberTable:
line 8: 0
line 9: 2
line 10: 9
Используя Integer.toString
, измените только invokedynamic
на invokestatic
:
3: invokestatic #2 // Method java/lang/Integer.toString:(I)Ljava/lang/String
Компилятор не пытается быть интеллектуальным в этом случае и не оптимизирует "" + int
.
Если вы читаете Javado c из java.lang.invoke.StringConcatFactory.makeConcatWithConstants(Lookup, String, MethodType, String, Object...)
, он ссылается на JLS 15.18.1 и JLS 5.1.11 .
JLS 15.18.1 объясняет операцию конкатенации из String + Не строка :
Если только одно выражение операнда имеет тип String, то преобразование строки (§5.1.11) выполняется для другого операнд для создания строки во время выполнения.
В JLS 5.1.11 объясняется, как преобразовать int
в String
:
Значение x примитивного типа T сначала преобразуется в ссылочное значение, как если бы оно передавалось в качестве аргумента соответствующему выражению создания экземпляра класса (§15.9):
If T is byte, short, or int, then use new Integer(x).
Чтобы ответить на ваш вопрос:
Я обнаружил, что это необычный способ преобразования int в строку. И все исследования, которые я провел, указывали мне на традиционные методы обращения. Так у кого-нибудь есть объяснение этому? И это даже "хорошая практика"?
Что необычно в вашем случае, если тот факт, что String идет после числа, а не до (как в "privacyLevel: " + privacyLevel
), но это не странно, учитывая JLS 15.18.1 .
Я не могу сказать, что это хорошая практика, хотя она и относительна, но я бы сказал, что это наследие практика, рожденная для того факта, что Integer.toString
не является такой старый (я не могу вспомнить, был ли он добавлен в Java 5 или 6) и что проще было сделать n + ""
или "" + n
.
Я бы лично поддержал Integer.toString
, потому что Я нахожу n + ""
довольно некрасивым. Это также может быть лучше с точки зрения производительности из-за сложности преобразования, выполненного в противном случае. К счастью для вас или моего ответа, кто-то сделал JMH-тест .
И последнее, но не менее важное: если вы будете придерживаться конкатенации, результат будет зависеть от версии компилятора, который будет выполнять преобразование:
- Вы используете Android Studio, и то, что применимо к vanilla Java, может быть не полностью применимо здесь.
- Java 8 используйте
StringBuilder
для генерации int 'String. - Java 11 используют
invokedynamic
и много чего сложного (для меня), чтобы объяснить, но я предполагаю, что он делает свою работу и работает так же хорошо, если лучше, чем StringBuilder
. Integer.toString
, кажется, оптимизирован в новой JVM горячей точки (он аннотирован @HotSpotIntrinsicCandidate
в Java 13).