programming-languages - 如何避免在动态类型语言中创建临时类型系统?

标签 programming-languages functional-programming types erlang

在我用没有类型系统的语言开始的每个项目中,我最终都开始发明一个运行时类型系统。也许“类型系统”这个词太强了;至少,当我处理复杂的数据类型时,我创建了一组类型/值范围验证器,然后我觉得需要对可以在哪里创建和修改数据类型保持偏执。

直到现在我才考虑过。作为一个独立的开发者,我的方法已经在一些小项目中得到了实践,现在没有理由停止工作。

尽管如此,这一定是错误的。我觉得好像我没有“正确”使用动态类型语言。如果我必须发明一个类型系统并自己执行它,我还不如使用一种以类型开头的语言。

所以,我的问题是:

  • 是否存在避免使用或发明类型系统的必要性的现有编程范式(对于没有类型的语言)?
  • 关于如何解决静态类型在动态类型语言中解决的问题(没有笨拙地重新发明类型),是否有其他常见的建议?


  • 这是一个具体的例子供您考虑。我正在使用 erlang(一种动态的强类型语言)中的日期时间和时区。这是我使用的常见数据类型:
    {{Y,M,D},{tztime, {time, HH,MM,SS}, Flag}}
    

    ...在哪里 {Y,M,D}是表示有效日期的元组(所有条目都是整数),tztimetime是原子,HH,MM,SS是表示正常的 24 小时时间的整数,Flag是原子之一 u,d,z,s,w .

    此数据类型通常从输入中解析,因此为了确保有效输入和正确的解析器,需要检查值的类型正确性和有效范围。稍后,这种数据类型的实例会相互比较,这使得它们的值的类型更加重要,因为所有术语都比较。来自 erlang reference manual
    number < atom < reference < fun < port < pid < tuple < list < bit string
    

    最佳答案

    除了静态与动态以及强与弱类型的混淆之外:

    大多数现有的静态类型系统并没有真正解决您想要在示例中实现的内容。无论您拥有什么类型的系统,通常都会在运行时检查范围检查和复杂性,例如 2 月 31 日,尤其是解析的输入。

    您在 Erlang 中的示例我有一些建议:

  • 使用记录。除了由于很多原因而有用和有帮助之外,它还可以让您轻松进行运行时类型检查,而无需付出很多努力,例如:
    is_same_day(#datetime{year=Y1, month=M1, day=D1}, 
                #datetime{year=Y2, month=M2, day=D2}) -> ...
    

    Effortless 仅匹配两个日期时间记录。如果源不受信任,您甚至可以添加 guard 来检查范围。并且它符合 erlangs let it crash 的错误处理方法:如果没有找到匹配项,则会得到一个 badmatch,并且可以在适当的级别(通常是主管级别)上进行处理。
  • 通常写你的代码,当假设无效时它会崩溃
  • 如果这感觉不够静态检查:使用 typerdialyzer为了找到可以静态发现的错误类型,将在运行时检查剩余的错误。
  • 不要对你的函数太严格你接受什么“类型”,有时即使对不同的输入做一些有用的附加功能比检查每个函数的类型和范围更有值(value)。如果您在重要的地方执行此操作,您通常会及早发现错误,以便轻松修复。对于你总是知道每个值来自哪里的函数式语言来说尤其如此。
  • 关于programming-languages - 如何避免在动态类型语言中创建临时类型系统?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/4456944/

    相关文章:

    java - Java 中的泛型和子类型问题

    php - 在 Ruby 中等同于 PHP 的 dirname(__FILE__)?

    c函数向下舍入一半

    functional-programming - 这可以被认为是一个纯函数(函数式编程)吗?

    functional-programming - 为什么在 Julia 中对类型(而不是变量)设置了不变性?

    c++ - 为什么声明 int* p1, p2; 中的 p2 不是指针类型?

    mysql - 将 BIGINT UNSIGNED 转换为 INT

    php - 如何在服务器上连续执行程序?使用哪种语言?

    c# - 如何在 C# 函数库中正确划分代码?

    模板类型的 C++ 运行时决策