I’m not a network programmer or language designer by trade, so I expect to be missing something here, but I’ll give it a go to learn where I’m wrong.
If you’re using distinct interfaces for distinct states (as it seems you are in your latter examples) and your compiler is going to enforce them, then shadowing variables (as a language feature) lets you unassign them as you go along. In a language I’m more familiar with, which uses polymorphic types rather than interfaces:
let socket = socks5_socket () in
let socket = connect_unauthenticated socket ~proxy in
let socket = connect_tcp socket address in
enjoy socket ();
with signatures:
val sock5_socket : unit -> [> `Closed of Socket.t]
val connect_unauthenticated : [< `Closed of Socket.t] -> proxy:Address.t -> [> `Authenticated of Socket.t]
val connect_tcp -> [< `Authenticated of Socket.t] -> Address.t -> [> `Tcp_established of Socket.t]
val enjoy : [< `Tcp_established of Socket.t] -> unit -> unit
so that if you forget the connect_unauthenticated line (big danger of shadowing as you mutate), your compiler will correct you with a friendly but stern:
This expression has type [> `Closed of Socket.t] but an expression was expected of type [< `Authenticated of Socket.t].
Of course, shadowing without type-safety sounds like a nightmare, and I’m not claiming that any language you want to use actually supports it as syntax. But I occasionally appreciate it (given, of course, that I’ve got a type inspector readily keybound, to query what state my socket is in at this particular point).
I’m not a network programmer or language designer by trade, so I expect to be missing something here, but I’ll give it a go to learn where I’m wrong.
If you’re using distinct interfaces for distinct states (as it seems you are in your latter examples) and your compiler is going to enforce them, then shadowing variables (as a language feature) lets you unassign them as you go along. In a language I’m more familiar with, which uses polymorphic types rather than interfaces:
with signatures:
so that if you forget the
connect_unauthenticated
line (big danger of shadowing as you mutate), your compiler will correct you with a friendly but stern:Of course, shadowing without type-safety sounds like a nightmare, and I’m not claiming that any language you want to use actually supports it as syntax. But I occasionally appreciate it (given, of course, that I’ve got a type inspector readily keybound, to query what state my socket is in at this particular point).