为什么/却ç允许隐函数和无类型的变量声明? [英] Why does/did C allow implicit function and typeless variable declarations?

查看:170
本文介绍了为什么/却ç允许隐函数和无类型的变量声明?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

为什么是明智的语言,让功能和无类型变量隐式声明?我得到的C是老了,但允许省略声明和默认 INT()(或 INT 中的情况下,变量)似乎不那么理智的我,甚至当时的情况。

那么,为什么它最初推出?当时它曾经真的有用吗?它实际上是(仍然)使用吗?

注:我知道,现代的编译器给你(在其标志你通过他们视)警告,并可以坐席preSS此功能。这不是问题!


例如:

  INT的main(){
  静电棒= 7; //默认为int栏
  回到了foo(bar); //默认为诠释富()
}INT美孚(int i)以{
  返回我;
}


解决方案

请参阅丹尼斯里奇的C语言开发:的 http://cm.bell-labs.com/who/dmr/chist.html

例如,


  

在相反过程中发生的普遍的语法变异
  创作的B,BCPL-其类型结构的核心语义内容
  和前pression评价规则,仍然完好无损。两种语言都
  无类型,或者说有一个单一的数据类型,字或细胞,一
  固定长度的位模式。内存这些语言包括一个
  这样的单元的线性阵列,并且一个单元格的内容的含义
  取决于所施加的操作。 +操作,例如,简单地
  增加了其操作数使用机器的整数加法指令,而
  其它算术运算同样无意识的实际的
  这意味着他们的操作数。因为存储器是一个线性阵列,它是
  可以跨preT在这个阵列中的细胞为指标的价值,
  和BCPL提供一个操作员用于此目的。在原来的
  语言它被拼写RV,后来!,而B使用一元*。
  因此,如果P是包含的索引的小区(或地址,或
  指针)另一个小区,* P指的是指向的的内容
  细胞,无论是作为在一个前pression或作为一个目标的值
  分配。


这typelessness用C一直持续到作者开始将其与不同字长移植到机器:


  

在此期间的语言的变化,特别是在1977年,在很大程度上集中在移植和类型安全的考虑,
  在努力对付的问题,我们预见到,并在观察
  移动相当体$ C $的c至新Interdata平台。猫
  当时还体现了其无类型起源的强烈迹象。
  指针,例如,险险从整体内存区别
  在指数的早期语言手册或现存code;的相似性
  字符指针和无符号整数的算术性质
  使得它难以抗拒的诱惑,识别它们。无符号
  添加类型以无符号运算,而不提供
  与指针操作混淆了。同样地,初语言
  整数和指针,但这种做法纵容之间分配
  开始气馁;类型转换的符号(被称为
  从陵68的例子`投下')被发明指定类型
  转换更明确。通过PL / I,C早期的例子受骗
  没有坚定地绑结构指针指向它们的结构
  到,并允许程序员编写指针 - >成员几乎不用
  关于指针的类型;这样的前pression拍摄
  不加鉴别地以被指定的存储器的区域的参考
  指针,而只有指定的成员名称的偏移量和类型。


编程语言演变为编程实践的变化。在现代C和现代的编程环境中,许多程序员从来没有写过汇编语言的概念,整形和指针是可以互换的可能似乎深不可测几乎和不合理。

Why is it sensible for a language to allow implicit declarations of functions and typeless variables? I get that C is old, but allowing to omit declarations and default to int() (or int in case of variables) doesn't seem so sane to me, even back then.

So, why was it originally introduced? Was it ever really useful? Is it actually (still) used?

Note: I realise that modern compilers give you warnings (depending on which flags you pass them), and you can suppress this feature. That's not the question!


Example:

int main() {
  static bar = 7; // defaults to "int bar"
  return foo(bar); // defaults to a "int foo()"
}

int foo(int i) {
  return i;
}

解决方案

See Dennis Ritchie's "The Development of the C Language": http://cm.bell-labs.com/who/dmr/chist.html

For instance,

In contrast to the pervasive syntax variation that occurred during the creation of B, the core semantic content of BCPL—its type structure and expression evaluation rules—remained intact. Both languages are typeless, or rather have a single data type, the 'word', or 'cell', a fixed-length bit pattern. Memory in these languages consists of a linear array of such cells, and the meaning of the contents of a cell depends on the operation applied. The + operator, for example, simply adds its operands using the machine's integer add instruction, and the other arithmetic operations are equally unconscious of the actual meaning of their operands. Because memory is a linear array, it is possible to interpret the value in a cell as an index in this array, and BCPL supplies an operator for this purpose. In the original language it was spelled rv, and later !, while B uses the unary *. Thus, if p is a cell containing the index of (or address of, or pointer to) another cell, *p refers to the contents of the pointed-to cell, either as a value in an expression or as the target of an assignment.

This typelessness persisted in C until the authors started porting it to machines with different word lengths:

The language changes during this period, especially around 1977, were largely focused on considerations of portability and type safety, in an effort to cope with the problems we foresaw and observed in moving a considerable body of code to the new Interdata platform. C at that time still manifested strong signs of its typeless origins. Pointers, for example, were barely distinguished from integral memory indices in early language manuals or extant code; the similarity of the arithmetic properties of character pointers and unsigned integers made it hard to resist the temptation to identify them. The unsigned types were added to make unsigned arithmetic available without confusing it with pointer manipulation. Similarly, the early language condoned assignments between integers and pointers, but this practice began to be discouraged; a notation for type conversions (called `casts' from the example of Algol 68) was invented to specify type conversions more explicitly. Beguiled by the example of PL/I, early C did not tie structure pointers firmly to the structures they pointed to, and permitted programmers to write pointer->member almost without regard to the type of pointer; such an expression was taken uncritically as a reference to a region of memory designated by the pointer, while the member name specified only an offset and a type.

Programming languages evolve as programming practices change. In modern C and the modern programming environment, where many programmers have never written assembly language, the notion that ints and pointers are interchangeable may seem nearly unfathomable and unjustifiable.

这篇关于为什么/却ç允许隐函数和无类型的变量声明?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆