How I can return a function within itself? it’s li...
# announcements
i
How I can return a function within itself? it’s like def f(x): print(x) return f then I can do f(1)(2)(3)
j
return ::f
i
@jw then what its type is when the function return itself? it won’t produce an infinite type?
j
don't know. use an expression body and find out!
it gets rejected by the compiler
i
it seems we can’t do that in any static type-check language
s
Yup, the return type of
f
would be infinitely recursive:
(Int)->((Int)->((Int)->((Int)->... ...))))))))
i
@streetsofboston but if we’ve known the times what it would be called, then we can get the result type manually, fun f(x: Int): (Int) -> (Int) -> Any then we can call f(3)(5)(7)
j
to be fair, recursive types are allowed
s
@Ifvwm But then you cannot do
return ::f
, unless
f
returns a plain
Any
itself,...
@jw How do you declare such a recursive type in Kotlin?
i
@streetsofboston
Copy code
fun test(x:String):(String)->(String)->Any{
  println(x)
  return ::test
}

test(“1”)(“2”)(“3”)
s
But
::test
has the type
(String)->((String)->(String)->Any)
. Can that be coerced/cast to
(String)->(String)->Any
? If so, then
(String)->((String)->(String)->Any)
is a sub-type of
(String)->(String)->Any
...
i
actually I really don’t know about that sub-type stuff, I’m from Haskell, there’s no such thing like type inheritance
a->b->a is a->(b->a) in type level
s
😀 In other words, If so, is a
(String)->((String)->(String)->Any)
safely assignable to a
(String)->(String)->Any
...
But in this case there's one extra (String).... Is this true as well:
a -> a -> a -> b
is
a -> a -> b
?
i
@streetsofboston yes, but when it’s concreted then no
s
Then how can ::test be returned as a return-value to itself in Kotlin?
i
a is a type variable, genetic in java
a can be a->a even a->a->a but Int->Int and Int->Int->Int are definitely not the same
@streetsofboston actually I don’t know why it can...
s
You can construct the type-paramater
A
with a concrete type
Int
. If
A -> A
is
A
, shouldn't
Int -> Int
be
Int
(after constructing it with an
Int
)?
i
@streetsofboston that’s polymorphic
Int->Int and (Int->Int)->(Int->Int) both are a->a, I think
s
Or is this possible because of type erasure in JVM? In JVM
(A)->A
is ambiguous with any other lambda that looks like
(A)->.... ....
Now I'm very curious! 😀
i
I don’t know type erasure in java well, but that Haskell guys tell me Java’s generics is very different with Haskell’s type variables, also some people call Java’s generics is a false polymorphic
s
It's almost midnight here....I'm going to
(Z)->(Z)->(Z)->(Z)->(Z)
💤
i
@streetsofboston good night!
b
Copy code
lateinit var f: (String) -> ((String) -> Any)
f = {
    print(it)
    f
}

f("1")("2")("3")
m
Not quite a function, but works like it. https://pl.kotl.in/tFUO00goe
Copy code
object test {
    operator fun invoke(i: Int) = also {
        println(i)
    }
}

fun main() {
    test(0)(1)(2)(3)(4)
}
👍 4