@@ -191,32 +191,50 @@ internal class CgKotlinRenderer(context: CgContext, printer: CgPrinter = CgPrint
191
191
element.right.accept(this )
192
192
}
193
193
194
- override fun visit (element : CgTypeCast ) {
195
- print (" (" )
196
- element.expression.accept(this )
194
+ /* *
195
+ * Sometimes we can omit rendering type cast and simply render its [CgTypeCast.expression] instead.
196
+ * This method checks if the type cast can be omitted.
197
+ *
198
+ * For example, type cast can be omitted when a primitive wrapper is cast to its corresponding primitive (or vice versa),
199
+ * because in Kotlin there are no primitive types as opposed to Java.
200
+ *
201
+ * Also, sometimes we can omit type cast when the [CgTypeCast.targetType] is the same as the type of [CgTypeCast.expression].
202
+ */
203
+ private fun isCastNeeded (element : CgTypeCast ): Boolean {
204
+ val targetType = element.targetType
205
+ val expressionType = element.expression.type
206
+
207
+ val isPrimitiveToWrapperCast = targetType.isPrimitiveWrapper && expressionType.isPrimitive
208
+ val isWrapperToPrimitiveCast = targetType.isPrimitive && expressionType.isPrimitiveWrapper
209
+ val isNullLiteral = element.expression == nullLiteral()
210
+
211
+ if (! isNullLiteral && element.isSafetyCast && (isPrimitiveToWrapperCast || isWrapperToPrimitiveCast)) {
212
+ return false
213
+ }
214
+
197
215
// perform type cast only if target type is not equal to expression type
198
216
// but cast from nullable to not nullable should be performed
199
217
// TODO SAT-1445 actually this safetyCast check looks like hack workaround and possibly does not work
200
218
// so it should be carefully tested one day
201
- if (! element.isSafetyCast || element.expression.type != element.targetType) {
202
- // except for the case when a wrapper is cast to its primitive or vice versa
203
-
204
- val isCastFromPrimitiveToWrapper = element.targetType.isPrimitiveWrapper &&
205
- element.expression.type.isPrimitive
206
- val isCastFromWrapperToPrimitive = element.targetType.isPrimitive &&
207
- element.expression.type.isPrimitiveWrapper
208
- val isNullLiteral = element.expression == nullLiteral()
209
- if (! isNullLiteral && element.isSafetyCast && (isCastFromPrimitiveToWrapper || isCastFromWrapperToPrimitive)) {
210
- return
211
- }
219
+ return ! element.isSafetyCast || expressionType != targetType
220
+ }
221
+
222
+ override fun visit (element : CgTypeCast ) {
223
+ if (! isCastNeeded(element)) {
224
+ element.expression.accept(this )
225
+ } else {
226
+ print (" (" )
227
+
228
+ element.expression.accept(this )
212
229
213
230
if (element.isSafetyCast) print (" as? " ) else print (" as " )
214
231
print (getKotlinClassString(element.targetType))
215
232
renderTypeParameters(element.targetType.typeParameters)
216
233
val initNullable = element.type.isNullable
217
234
if (element.targetType.isNullable || initNullable) print (" ?" )
235
+
236
+ print (" )" )
218
237
}
219
- print (" )" )
220
238
}
221
239
222
240
override fun visit (element : CgErrorWrapper ) {
0 commit comments