For what it's worth: it's _very_ rare for a type annotation to be required in Haskell. It's just considered best practice (supported by compiler warning options) to have them on all top-level declarations, for two reasons:
- it's a good extra layer of _human-readable_ documentation about basic behavior and requirements (as in this article); and
- it lets the compiler give better error messages.
The compiler is _always_ going to do its own inference, whether you give it a signature or not. If it infers a valid type _which isn't the one you thought you wrote_, and you didn't specify what the type _should_ be, that function/statement will compile -- you won't get an error until later, when you attempt to consume it and the types don't match. This can be harder to trace, especially if there's a bunch of polymorphic code in the middle where any type will pass. Supplying a manual annotation lets the compiler immediately say "hey, these don't match."
Frequencies are heavily regulated in the US as well. There are a handful of public bands, but anything else requires FCC licensing to use. Broadcast power is also restricted.
Of course, Germany could still be more restrictive, I don't know the law there! But there must be a fairly simple licensing path for some microwave bands, or nobody would be able to sell wireless routers. This is the same general class of equipment, so unless there's too much restriction on broadcast power to connect at kilometer+ ranges (with a focused directional antenna, rather than the broadcast antenna of a router!) there should be a way to make it work.
- it's a good extra layer of _human-readable_ documentation about basic behavior and requirements (as in this article); and
- it lets the compiler give better error messages.
The compiler is _always_ going to do its own inference, whether you give it a signature or not. If it infers a valid type _which isn't the one you thought you wrote_, and you didn't specify what the type _should_ be, that function/statement will compile -- you won't get an error until later, when you attempt to consume it and the types don't match. This can be harder to trace, especially if there's a bunch of polymorphic code in the middle where any type will pass. Supplying a manual annotation lets the compiler immediately say "hey, these don't match."