# No null safety when generics are in play?

**URL:** <https://discuss.kotlinlang.org/t/no-null-safety-when-generics-are-in-play/6161>\
**Category:** Support\
**Created:** [January 9, 2018, 1:50pm UTC](https://discuss.kotlinlang.org/t/no-null-safety-when-generics-are-in-play/6161 "2018-01-09T13:50:30Z")\
**Posts on this page:** 10\
**Page:** 1

<div class="post-metadata">

**Author:** ![reitzig](https://sea1.discourse-cdn.com/flex019/user_avatar/discuss.kotlinlang.org/reitzig/32/6970_2.png) [@reitzig](https://discuss.kotlinlang.org/u/reitzig)\
**Post date:** [January 9, 2018, 1:50pm UTC](https://discuss.kotlinlang.org/t/no-null-safety-when-generics-are-in-play/6161/1 "2018-01-09T13:50:30Z")

</div>

Consider this simple code:

```kotlin
data class Wrap<T>(var raw: T) {
    val size
        get() = raw.toString().length
}

fun main(args: Array<String>) {
    val test: Wrap<Integer?> = Wrap(null)
    println(test.size)
}

```

I expect some kind of failure here.

1. The compiler might complain at `raw.toString()` that `raw` may be `null`.
2. The compiler might complain that `Integer?` is not a permissible type parameter for `Wrap`.
3. We get an NPE when executing `test.size`.

We get … nothing. The code runs, printing an empty line.  
(When calling from Java, due to silently added platform types (I assume?) things even get a more interesting.)

What’s going on here?

---

<div class="post-metadata">

**Author:** ![mattmook](https://sea1.discourse-cdn.com/flex019/user_avatar/discuss.kotlinlang.org/mattmook/32/4637_2.png) [@mattmook](https://discuss.kotlinlang.org/u/mattmook)\
**Post date:** [January 9, 2018, 2:03pm UTC](https://discuss.kotlinlang.org/t/no-null-safety-when-generics-are-in-play/6161/2 "2018-01-09T14:03:41Z")

</div>

I’ve been caught out by this myself, and the reason is hidden in the documentation at [https://kotlinlang.org/docs/reference/generics.html](https://kotlinlang.org/docs/reference/generics.html)

> The default upper bound (if none specified) is Any?.

i.e. `T` in your example is always treated as an optional.

Simply by changing `T` to be bound to `Any` it will add in the null checks you expect to the Wrap class.

---

<div class="post-metadata">

**Author:** ![ilya.gorbunov](https://sea1.discourse-cdn.com/flex019/user_avatar/discuss.kotlinlang.org/ilya.gorbunov/32/1645_2.png) [@ilya.gorbunov](https://discuss.kotlinlang.org/u/ilya.gorbunov)\
**Post date:** [January 9, 2018, 2:21pm UTC](https://discuss.kotlinlang.org/t/no-null-safety-when-generics-are-in-play/6161/3 "2018-01-09T14:21:15Z")

</div>

> [@reitzig](#):
>
> We get … nothing. The code runs, printing an empty line.

Are you sure you get an empty line? Because I get “4” printed. Which is the length of the string `"null"` that is the result of `null.toString()`

None of the failures or compiler errors should happen in your code:

1. `raw.toString()` is allowed because `toString()` is an extension for `Any?`
2. `Integer?` is allowed substitution for `T` because `T` has nullable upper bound, namely `Any?`
3. NPE doesn’t happen, again because `toString()` is an extension that can handle nullable recevier.

---

<div class="post-metadata">

**Author:** ![reitzig](https://sea1.discourse-cdn.com/flex019/user_avatar/discuss.kotlinlang.org/reitzig/32/6970_2.png) [@reitzig](https://discuss.kotlinlang.org/u/reitzig)\
**Post date:** [January 9, 2018, 3:19pm UTC](https://discuss.kotlinlang.org/t/no-null-safety-when-generics-are-in-play/6161/4 "2018-01-09T15:19:28Z")

</div>

Thanks for the reference! I suspected something like that but couldn’t get it to match that `toString()` would be accepted on an optional type.

---

<div class="post-metadata">

**Author:** ![reitzig](https://sea1.discourse-cdn.com/flex019/user_avatar/discuss.kotlinlang.org/reitzig/32/6970_2.png) [@reitzig](https://discuss.kotlinlang.org/u/reitzig)\
**Post date:** [January 9, 2018, 3:22pm UTC](https://discuss.kotlinlang.org/t/no-null-safety-when-generics-are-in-play/6161/5 "2018-01-09T15:22:13Z")

</div>

> [@ilya.gorbunov](#):
>
> Are you sure you get an empty line? Because I get “4” printed.

Ah, me too. Sorry, my bad. Must have gotten lost in a series of prints.

> [@](#):
>
> toString() is an extension that can handle nullable recevier

I think this is the core of my confusion. It’s surprising to me that `null` should accept _any_ method call; it certainly doesn’t in Java! But `Wrap` is even fine when we call it from Java, passing it Java `null`.

I remain puzzled why this would be Kotlin’s semantics, but thanks for the explanation!

---

<div class="post-metadata">

**Author:** ![ilya.gorbunov](https://sea1.discourse-cdn.com/flex019/user_avatar/discuss.kotlinlang.org/ilya.gorbunov/32/1645_2.png) [@ilya.gorbunov](https://discuss.kotlinlang.org/u/ilya.gorbunov)\
**Post date:** [January 9, 2018, 5:29pm UTC](https://discuss.kotlinlang.org/t/no-null-safety-when-generics-are-in-play/6161/6 "2018-01-09T17:29:50Z")

</div>

> [@reitzig](#):
>
> It’s surprising to me that null should accept any method call

`null` does not allow to call _any_ method on it. Only the _extensions_ that allow nullable receivers can be invoked on `null` receiver, e.g:

```auto
fun Any?.toString(): String
fun String?.equals(other: String?, ignoreCase: Boolean = false): Boolean
fun T.let(f: (T) -> R): R // because T is generic with Any? upper bound

```

---

<div class="post-metadata">

**Author:** ![madmax1028](https://sea1.discourse-cdn.com/flex019/user_avatar/discuss.kotlinlang.org/madmax1028/32/3335_2.png) [@madmax1028](https://discuss.kotlinlang.org/u/madmax1028)\
**Post date:** [January 9, 2018, 7:43pm UTC](https://discuss.kotlinlang.org/t/no-null-safety-when-generics-are-in-play/6161/7 "2018-01-09T19:43:55Z")

</div>

Remember to always write:

```auto
data class Wrap<T : Any>(var raw: T)

```

by default generic types allow implicitly on `null` values like this:

```auto
data class Wrap<T {{: Any?}}>(var raw: T)

```

then compiler will ensure that everywhere you use `T` you will only have non-nullable types.

---

<div class="post-metadata">

**Author:** ![reitzig](https://sea1.discourse-cdn.com/flex019/user_avatar/discuss.kotlinlang.org/reitzig/32/6970_2.png) [@reitzig](https://discuss.kotlinlang.org/u/reitzig)\
**Post date:** [January 9, 2018, 8:01pm UTC](https://discuss.kotlinlang.org/t/no-null-safety-when-generics-are-in-play/6161/8 "2018-01-09T20:01:59Z")

</div>

I meant, “any at all”. Anyway, “`null` as a value” will take some getting used to, especially in situations of interop.

---

<div class="post-metadata">

**Author:** ![reitzig](https://sea1.discourse-cdn.com/flex019/user_avatar/discuss.kotlinlang.org/reitzig/32/6970_2.png) [@reitzig](https://discuss.kotlinlang.org/u/reitzig)\
**Post date:** [January 9, 2018, 8:02pm UTC](https://discuss.kotlinlang.org/t/no-null-safety-when-generics-are-in-play/6161/9 "2018-01-09T20:02:50Z")

</div>

Thanks. I think I got foreign-languaged; in Swift, `T` is equivalent to `T: Any` and you write `T?` to get the equivalent of `T: Any?`.

---

<div class="post-metadata">

**Author:** ![madmax1028](https://sea1.discourse-cdn.com/flex019/user_avatar/discuss.kotlinlang.org/madmax1028/32/3335_2.png) [@madmax1028](https://discuss.kotlinlang.org/u/madmax1028)\
**Post date:** [January 9, 2018, 8:15pm UTC](https://discuss.kotlinlang.org/t/no-null-safety-when-generics-are-in-play/6161/10 "2018-01-09T20:15:15Z")

</div>

More less
