首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >类型推断是如何在C++11或Go这样的语言中实现的?

类型推断是如何在C++11或Go这样的语言中实现的?
EN

Stack Overflow用户
提问于 2016-10-25 21:15:04
回答 1查看 312关注 0票数 0

我在这里看到了this的问题,但它并没有特别详细地回答我的想法。如果像Go或C++11这样的语言没有使用像Damas这样的推理算法,那么它们到底是做什么的呢?我认为这不像右手边的类型那么简单,因为如果你有这样的东西:

代码语言:javascript
复制
5 + 3.4

编译器将如何破译这是哪种类型?有没有哪种算法不像

代码语言:javascript
复制
if left is integer and right is float:
    return float;
if left is float and right is integer:
    return float;
etc... for every possible pattern

如果你能用简单的语言来解释,那就太好了。我没有非常详细地研究编译器的构造或任何理论主题,我也不真正讲函数式语言或复杂的数学符号。

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2016-10-25 21:42:22

我认为这不像把类型放在右边那么简单

对于表单auto var = some_expression;的基本类型推断,它就是这么简单。每个良好类型的表达式都有一个类型,该类型将是var的类型。不存在从表达式类型到另一类型的隐式转换(如果为var提供显式类型,则可能存在这种转换)。

如果你有这样的东西: 5+ 3.4

5 + 3.4的类型是什么?”并不是特定于类型推断,C++编译器总是必须回答这个问题--甚至在引入类型推断之前。

所以让我们后退一步,看看C++编译器是如何对语句some_type var = some_expression;进行类型化的

首先,它确定some_expression的类型。因此,在代码中,您可以想象类似于Type exp_type = type_of(exp);的东西。现在,它检查exp_type是否等于some_type,还是存在从exp_typesome_type的隐式转换。如果是这样的话,语句是很好的类型,并且var作为some_type类型引入到环境中。否则就不是了。

现在,当我们引入类型推断并编写auto var = some_expression;时,方程发生了变化:我们仍然执行Type exp_type = type_of(exp);,但是没有将它与另一种类型进行比较或应用任何隐式转换,而是将exp_type设置为var的类型。

现在让我们回到5 + 3.4。它的类型是什么,编译器如何确定它?在C++中,它的类型是double。C++标准中列出了确定算术表达式类型的确切规则(查找“常规算术转换”),但基本上可以归结为:在两个操作数类型中,选择一个可以表示更大范围的值。如果类型小于int,则将两个操作数转换为int。否则,将两个操作数转换为所选择的类型。

在代码中,您可以通过为每个数字类型分配一个转换级别来实现这一点,然后执行如下操作:

代码语言:javascript
复制
Type type_of_binary_arithmetic_expression(Type lhs_type, Type rhs_type) {
    int lhs_rank = conversion_rank(lhs_type);
    int rhs_rank = conversion_rank(rhs_type);
    if(lhs_rank < INT_RANK && rhs_rank < INT_RANK) return INT_TYPE;
    else if(lhs_rank < rhs_rank) return rhs_type;
    else return lhs_type;
}

想必围棋的规则有些不同,但同样的原则适用。

票数 5
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/40249831

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档