Eta*_*tam 11 python java static-typing dynamic-typing
我来自Java世界,我想知道在编译代码时除了缺少错误外,Python中的动态类型有什么好处?
你喜欢Python的打字吗?你有一个例子,它在一个大项目中有所帮助吗?是不是有点容易出错?
Jör*_*tag 18
在一般情况下,静态类型检查是不可判定的.这意味着存在静态类型安全的程序,但是类型检查程序无法证明它们是静态类型安全的,因此类型检查器必须拒绝这些程序.
换句话说:类型检查程序不允许您编写的类型安全程序.或者,更简洁:静态类型阻止您编写某些程序.
这通常适用于所有静态类型,而不仅仅适用于Java.
至于Java:它有一个相当糟糕的类型系统.它的类型系统表达力不足以表达甚至非常简单的属性.例如:在类型static void java.util.Arrays.sort(Object[] a)中它实际上是说结果必须是,你知道,排序?或者数组元素必须部分排序?
Java的另一个问题是它的类型系统有很大的孔,你可以驾驶卡车通过:
String[] a = new String[1];
Object[] b = a;
b[0] = 1; // ArrayStoreException
Run Code Online (Sandbox Code Playgroud)
在这种特殊情况下的问题是协变阵列.数组根本不可能是协变的和类型安全的.
Java结合了静态类型的所有麻烦,没有任何优势.所以,你也可以摆脱麻烦.
但请注意,这不是普遍的.还有其他语言有更好的类型系统,其权衡不太清楚.
例如,这是Python中有史以来最愚蠢的语言基准(Fibonacci):
def fib(n):
if n < 2: return n
return fib(n-2) + fib(n-1)
Run Code Online (Sandbox Code Playgroud)
和Java:
int fib(int n) {
if (n < 2) return n;
return fib(n-2) + fib(n-1);
}
Run Code Online (Sandbox Code Playgroud)
请注意,那里存在更多混乱,这与静态类型有关.为了使比较更公平,让我们想象一下使用Python语法和Java语义的语言:
def fib(n: int) -> int:
if n < 2: return n
return fib(n-2) + fib(n-1)
Run Code Online (Sandbox Code Playgroud)
[有意思的是:与另外在Python 3.x的可选静态类型的注解,那就是实际上也是有效的Python代码,但它显然还没有静态的类型安全的,因为注释只是:注解.他们从未在任何地方进行实际检查.
还有就是一些明确的杂波出现.但是,在Haskell中它看起来像这样:
fib n
| n < 2 = n
| otherwise = fib (n-2) + fib (n-1)
Run Code Online (Sandbox Code Playgroud)
与Python版本不同,这是完全静态类型安全的,但没有类型相关的混乱.
在这种特殊情况下,静态和动态类型的好处之间的问题不太清楚.
顺便说一句,更惯用的Haskell版本可能看起来像这样:
fib 0 = 0
fib 1 = 1
fib n = fib (n-2) + fib (n-1)
Run Code Online (Sandbox Code Playgroud)
或这个:
fibs = 0 : 1 : zipWith (+) fibs (tail fibs)
Run Code Online (Sandbox Code Playgroud)
实际上,Java和Python之间更重要的区别并不在于Java是静态类型的而且Python是动态类型的,而是Java不是一种优秀的编程语言,而Python 则是.所以,Java总是会失败,不是因为它是静态类型的,而是因为它是垃圾.比较BASIC和Haskell,Haskell明显获胜,但同样,不是因为它是静态类型的,而是因为BASIC是垃圾.
更有趣的比较是Java vs. BASIC或Python vs. Haskell.
Dav*_*rby 12
我怀疑绝大多数非平凡的Java程序都有动态类型.
每次在Java中,您都要从Object转换为显式类型,而您正在进行动态类型检查 - 这包括在1.5中引入泛型之前对集合类的每次使用.实际上Java泛型仍然可以推迟一些类型检查直到运行时.
每次使用Java反射时,都会进行动态类型检查.这包括从文本文件中的类或方法名称到实际类或方法的映射 - 例如,每次使用Spring XML配置文件时.
这是否会使Java程序变得脆弱且容易出错?Java程序员是否花费大量时间来跟踪和修复错误动态类型的问题?可能不是 - 也不是Python程序员.
动态类型的一些优点:
Do you like it in Python?
It's part of Python. Liking it in Python is silly.
Do you have an example where it helped in a big project?
Yes. Every single day I rejoice that I can make changes and -- because of Duck typing -- they are reasonably localized, pass all the unit tests, pass all the integration tests, and nothing is disrupted elsewhere.
If this was Java, the changes would require endless refactoring to pull interfaces out of classes so that I could introduce variations that were still permitted under Java's static type checking.
Doesn't it a bit error prone?
Not any more than static typing is. A simple unit test confirms that the objects conform to the expected features.
It's easy to write a class in Java that (a) passes compile-time checks and (b) crashes horribly at run time. Casts are a good way to do this. Failing to meet the classes intent is a common thing -- a class may compile but still not work.
这会减轻你的负担。您可以将红色视为“Red”(常量)、“255, 0, 0”(元组)或“#FF0000”(字符串):三种不同的格式,这将需要三种不同的类型或复杂的查找以及Java中的转换方法。
它使代码更简单。
| 归档时间: |
|
| 查看次数: |
1834 次 |
| 最近记录: |