Are inferred types "frozen" for crystal shards and the standard library?

So, Crystal is pretty unique about how it types things.

If you feed it this:

def Object.from_json(string_or_io)
  parser = JSON::PullParser.new(string_or_io)
  new parser
end

you might think, based on how other languages work (particularly Haskell or Elm, where you can omit the types of arguments and the compiler will infer them), that the compiler will infer the type of that method and conclude that string_or_io is String | IO.

However, that’s not how Crystal works.

The way Crystal works is that methods are always untyped. The compiler doesn’t know their type, and there’s no need to know their type. They only get a type, and this type is not assigned to the method but rather to an instantiation of a method (think C++ templates, or generics), when you call a method. Just then the compiler will go ahead and infer the type of the body. But argument types are never inferred.

That’s why there’s no “lock down” types from shards or from anything.

And all of this is of course related to “why it’s difficult to do incremental compilation in Crystal”.

4 Likes