5 ms·
Except that to perform the level of checks that a compiler does with a good type system, you would have to write a large amount of tests. Code is a liability, a
by sbergot 12y ago
Except that to perform the level of checks that a compiler does with a good type system, you would have to write a large amount of tests. Code is a liability, and testing code is no exception.
Writing tests in static languages is still required. You just have to write a smaller amount of them. What's more, type checking is enforced in a more systematic way. With tests, you have to rely on people to write them. If a type system is well designed, people will use it to model their code, and the type checking is done automatically.
What's more, types should not be reduced to the type checking phase. Types are a way to provide a high level model/structure. You still need this if you are working in a medium/large project. With static types, this model have nicer semantics, and is more useful.
- nickbauman 12y agoOk try this: Go model a square and a rectangle in your favorite statically typed language. You will find that square extends rectangle and setting the length on a square also sets the width. So far so good? So if I have a collection of rectangles which contains an unknown number of squares of which I set the width on each of them. You can't answer the question as to whether the result is correct or not. And I have just destroyed your type system's purpose by using polymoronism, expectoration and dispossession, the three-legged stool of static typing OO, with a very simple and well-defined domain subset of geometry. Of course it's contrived but since I've been programming (which is longer than I care to say here, because it really dates me) this is basically where I'm at with static type systems. AS long as I've spent with them I find they're not as useful as they should be. I haven't tried Haskell (I probably should) but I'm getting too much done with dynamic languages, especially Lisps, to look back right now. Too much power to look away. Tschau!
- pjmlp 12y agoIn an enterprise project some would be changing the widht instead.
- the_why_of_y 12y agoWell if you have a Square type that's a subtype of Rectangle then you can't have methods on Rectangle that, when called on a Square instance, would invalidate the invariant of a Square. If your system is sufficiently dynamic (prototype-based?) you can exchange the class of an instance at runtime. If not, simply make your Rectangles immutable, so a setWith method returns a new instance and you can then return a new Rectangle or a new Square from a Rectangle's setWidth. That should work in any statically typed language with inclusion polymorphism.
- nickbauman 12y agoYes I think you're beginning to understand the point.
- codygman 12y ago> Go model a square and a rectangle in your favorite statically typed language. Okay. data Shape = Square Int | Rectangle Int Int deriving (Show) > You will find that square extends rectangle and setting the length on a square also sets the width. Why? I don't really see a need for square to extend a rectangle. > So if I have a collection of rectangles which contains an unknown number of squares of which I set the width on each of them. Like this? > let unknowns = [(5,4),(3,2),(4,4)] > let toShape (x,y) = if x == y then Square x else Rectangle x y > map toShape unknowns [Rectangle 5 4,Rectangle 3 2,Square 4] Tomorrow I'll see if I can make this type-safe by using dependent typing as shown in: [0][1][2] This was easily solvable in my staticly typed language as you can see. In something like Idris I could have very easily encoded the toShape function the the type signature. 0: http://www.alfredodinapoli.com/posts/2014-10-13-fun-with-dependent-types-in-haskell.html http://www.alfredodinapoli.com/posts/2014-10-13-fun-with-dep... 1: https://www.fpcomplete.com/user/konn/prove-your-haskell-for-great-safety/dependent-types-in-haskell https://www.fpcomplete.com/user/konn/prove-your-haskell-for-... 2: http://jozefg.bitbucket.org/posts/2014-08-25-dep-types-part-1.html http://jozefg.bitbucket.org/posts/2014-08-25-dep-types-part-...
- pfultz2 12y agoThats cool. Here's the somewhat equivalent in C++: struct square { int x; }; struct rectangle { int x; int y; }; boost::variant<square, rectangle> to_shape(int x, int y) { if (x == y) return square(x); else return rectangle(x, y); } std::vector<std::pair<int, int>> unknowns = { {5, 4}, {3, 2}, {4, 4} }; auto shapes = unknowns | boost::adaptors::transformed(boost::fusion::make_fused(to_shape)); Of course, the structs are not polymoprhic and can't be printed out. I just left that out because it requires a little more code to do that. Obviously with haskell its much less code. I would very much be interested in the dependently typed version.
- codygman 12y agoCool, it's always good to see other languages approaches (especially when idiomatic) to try out their way of thinking. > I would very much be interested in the dependently typed version. I'll try to get to it later today, I'm pretty busy until then.
- dllthomas 12y ago"with a very simple and well-defined domain subset of geometry." I don't think you're actually working with a well-defined subset of geometry. What is breaking here is the notion of persistent identity over time - "take this square and change its width - leaving us with not a new square/rectangle but the same square changed" - which I don't recall encountering in geometry.
- dragonwriter 12y ago> Go model a square and a rectangle in your favorite statically typed language. You will find that square extends rectangle and setting the length on a square also sets the width. The coordinates of the vertices are part of the identity of a square and in any reasonable model of a square cannot be changed. An object with mutable size that is constrained to always be a square probably cannot be a member of a class which extends a class representing objects with mutable length and width that is constrained to remain a rectangle (but necessarily a square), since the properties of the former under mutation are not a simple extension of the properties of the latter, so that the two do not really have an is-a relationship (unless the transformations applicable to the two are designed in an unusual way -- as might be the case where the transformations on the rectangle were constrained to preserve the aspect ratio in all cases.) People often on initial analysis how mutability really destroys is-a relationships which are based on relations between immutable entities.
- nickbauman 12y agoMutability or not doesn't change the fundamental assertion that the result is not intuitive even to the author of the class hierarchy. My whole point is not whether the modeling of the problem in a typical type system is correct or not. The point is that a typical type system allows for a wide range of "incorrectness" that still compiles and runs and does exactly what it was designed to do but still leaves the programmer with an inscrutable result. Therefore, it can be seen, that there might be other, better ways to assert your system is correct than using types.
- lmm 12y ago> You will find that square extends rectangle and setting the length on a square also sets the width. "setting the length"?? Do you mean "making a copy with the length set to a different value"? If you have a square, which is-a rectangle, you can of course use the rectangle's copy function, or a rectangle lens or some such, to make a copy with a different length. Which will be a rectangle. Utterly trivial.