所有语言基本相同吗?


39

最近,我不得不了解一个用我不知道的语言编写的小程序的设计(ABAP,如果您必须知道的话)。我可以毫不费力地弄清楚。

我意识到掌握一种新语言是完全不同的球类游戏,但是如果您已经知道几种语言(最好是多种语言),那么直接理解任何一种语言的代码意图(特别是生产标准代码,不一定很复杂)都是很简单的。一种程序/ OO和一种功能)。

这通常是真的吗?所有编程语言是否都由类似的结构(如循环,条件语句和函数之间的消息传递)组成?是否存在典型的Java / Ruby / Haskell程序员无法理解的非深奥语言?所有语言都有共同的起源吗?


4
我将指导您了解Paul Graham的“ 击败平均水平”。您可能会或可能不想阅读全部内容,但是对于相关部分,请搜索​​标题“ The Blub Paradox”。格雷厄姆先生不会费心在文本墙上放置锚点,因此我无法直接链接到它。
克瓦特福德

4
语言没有共同的起源。但是所有语言都试图解决一些问题。我认为这有点类似于口头语言。目的是表达自己。我不能说基于1程序/ OO /功能的知识来理解语言是很直接的。我还没有做到这一点,但是如果我要问这个问题,我会看着带有很多括号的perl或lisp,而且我也不能说知道所有一种语言就足够了。
shahkalpesh

1
在这种情况下:Lambda演算。也许不是“真正的”语言,但从某种意义上讲,它是所有编程语言的母亲。我曾经不得不实现一种功能语言,以便将其编译为lambda表达式(然后直接对其进行解释)。尽管保留了所有相关的标识符,但结果(至少对我而言)还是不可读的。特别是使用Y组合器的递归函数。弄清楚某些样本表达式的功能的唯一实用方法是手动评估它们。像fibonnaci和merge sort这样的简单事物是不可读的。
克瓦特福德

2
如果您了解函数式语言,则应该知道并非每种语言都可能存在循环。
jalf

Piet完全不同。:)

Answers:


88

大多数程序语言的基础几乎相同。

他们提供:

  • 标量数据类型:通常为布尔值,整数,浮点数和字符
  • 复合数据类型:数组(字符串是特殊情况)和结构
  • 基本代码构造:标量上的算术,数组/结构访问,赋值
  • 简单的控制结构:if-then,if-then-else,while,for循环
  • 代码块包:函数,带参数的过程
  • 范围:标识符具有特定含义的区域

如果您了解这一点,那么您将掌握地球上90%的语言。使这些语言稍微难于理解的原因是人们用来说相同的基本事物的奇数语法令人难以置信。有些人使用涉及奇数标点的简洁表示法(APL是极端的)。有些使用很多关键字(COBOL是一个很好的代表)。没关系。重要的是,该语言本身是否足够完整,可以执行复杂的任务,而又不会导致头发脱落。(尝试在Window DOS shell脚本中对一些严重的字符串黑客进行编码:它具有Turing功能,但在所有方面确实很糟糕)。

更多有趣的程序语言提供

  • 嵌套或词法范围,名称空间
  • 指针允许一个实体通过动态存储分配引用另一个实体
  • 相关代码的打包:包,带有方法的对象,特征
  • 更复杂的控制:递归,延续,闭包
  • 专门的运算符:字符串和数组运算,数学函数

虽然从技术上讲,语言不是语言的财产,但这些语言所居住的生态系统的财产却是可以轻松访问或随语言一起作为开发工具的一部分提供的库。拥有广泛的库功能可以简化/加快编写应用程序的过程,这仅仅是因为不必重新发明库的功能。尽管人们普遍认为Java和C#本身就是好的语言,但使它们真正有用的是它们附带的巨大库以及易于获得的扩展库。

难以理解的语言是非过程语言:

  • 纯函数式语言,没有赋值或副作用
  • 逻辑语言,例如Prolog,在其中进行符号计算和统一
  • 模式匹配语言,您可以在其中指定与问题匹配的形状,并且动作通常由匹配触发
  • 约束语言,可让您指定关系并自动求解方程式
  • 硬件描述语言,其中所有内容并行执行
  • 特定领域的语言,例如SQL,彩色Petri网等。

语言有两种主要的表示样式:

  • 基于文本,其中标识符名称实体和信息流被隐式编码在使用标识符命名实体的公式中(Java,APL等)
  • 图形化,其中实体被绘制为节点,实体之间的关系被绘制为这些节点之间的显式弧(UML,Simulink,LabView)

图形语言通常允许文本子语言作为节点和弧上的注释。奥德(Odder)图形语言递归地允许在节点和弧上显示图形(带有文本:)。真正奇怪的图形语言允许注释图指向要注释的图。

这些语言中的大多数都基于极少数的计算模型:

  • Lambda演算(Lisp和所有功能语言的基础)
  • 发布系统(或字符串/树/图形重写技术)
  • 图灵机(状态修改和新存储单元的选择)

鉴于大多数行业都将重点放在过程语言和复杂的控制结构上,如果您很好地学习了该类别中一种更有趣的语言,尤其是如果它包含某种类型的面向对象的语言,您将得到很好的服务。

我强烈建议您学习Scheme,尤其是从一本非常出色的书: 《计算机程序的结构和解释》中。这描述了所有这些基本概念。如果您了解这些知识,那么其他语言似乎将非常简单,除了愚蠢的语法。


3
好答案!作为后续(是否可以在SO中提出后续问题?),我是否可以掌握一种语言并声称可以理解编程软件中的所有概念?会是Lisp(或方言,例如Scheme)吗?

@Anirudh:没有正式的跟进机制,但是您可以提出一个新问题。如果它包含原理和与此问题的链接,则它甚至可能不会关闭。;)为了回答您的问题,我衷心地相信,不仅存在一种语言,因为范例之间的差异太大。

@Anirudh:同意John Y,不只是一个。但是,如果您是该领域的新手,那么您应该花费大量精力来掌握过程范式(我认为OO只是一种专业)。通过其他范式(逻辑,约束,数据流)来了解它们的工作原理并没有什么坏处,但是对于大多数日常工业工作而言,过程语言几乎是最重要的。
伊拉·巴克斯特

1
就像自然语言一样,“难以理解”是主观的,并且取决于您学习的第一语言。
NullUserException 2011年

1
@NullUserException:这建议您应该谨慎选择母语,以最大程度地理解他人。这就是Scheme的重点,尤其是SICP的书。
伊拉·巴克斯特

6

硬件描述语言是编程语言,但是它们在概念上有很大的不同。尝试使用VHDL或Verilog以获得大小。它们在FPGA编程中很常见。(好吧,它们不是处理器,而是通用计算设备。对于计算机科学主题,应将其视为有效的硬件。)您必须明确地使事情串行发生。这是一个完全不同的模型。您认为并行发生的事情是规则,而不是例外。Verilog中的For循环扩展为并行硬件。因此,“预期”行为可能不是您期望的。


那是个很好的观点。我将查找Verilog / VHDL。

我一直认为传统的编程语言只是编写诸如VHDL之类的自然并行程序的非常糟糕的方法。当您以硬件设计师的身份开始时,有关串行发生的所有事情的这些内容似乎非常笨拙。(我们正在向人们传授错误的编程语言,这是他们的第一门语言:应该是Verilog!)。
艾拉·巴克斯特

4

取决于您所说的“基本”。所有具有灵活性的语言都是图灵完备的。从这个意义上说:是的,它们基本上都是相同的。

在较低的级别上,它们都执行相似的操作序列,并且所有Windows,Linux和(最新)OS X素材都使用相同的指令集在Intel兼容处理器上运行。这样,它们也基本相同。

我意识到您已经在问题中“基本”地定义了,但是要真正回答它,该定义必须更加完善。在许多方面,它们都是相似的。在许多方面,它们是不同的。说“取决于”很容易。如果您采取任何一种极端做法,问题都可能无法回答您的意图,因此划界线对于按照您的意图回答问题至关重要。


3

我会说一种语言编码含义。如果含义在某些上下文中具有任何意义,则可以表示该含义的所有语言都可以说是等效的,受该含义和上下文的限制。

如果将上下文限制为标准的冯·诺依曼机器,则可以说更改内存和在cpu中进行计算的计算含义是起源-可能是所有语言都具有的唯一含义。所有其他事物都是基于这些事物的抽象。


1
约翰·冯·诺依曼(John von Neumann)。它的发音不像“ newman”,更像“ noyman”。

感谢您的纠正-我的发音确实和您说的一样。
Preet Sangha,2009年

当有人提出更正建议时,您可以编辑您的帖子以反映出来。
菲尔·米勒

2

编程语言也是思考的工具。从另一种思维角度来看,有些问题消失了,或者转变为其他更易管理的问题(例如,许多C ++样式设计模式只是在您使用Lisp进行思考时才消失(例如,参见Peter Norvik的演示文稿),而Erlang使您摆脱了思考一些低级并发或分布式计算结构,让您仅专注于应用程序逻辑)。

但是请注意,有时“新”范例可以部分地应用于“旧”编程语言,这解释了为什么我们例如拥有书籍来教Java程序员进行功能编程。但是,在语言级别上本地支持和集成更强大的范式可以使范式更自然地应用(因此,如其他答案所暗示的那样,无法用支持陌生范式的语言来理解程序-@Ira Baxter列出了非过程语言和@kwatford指的是Paul Graham)。


2
+++++++[>+++++++++++<-]>+.<+++++++++++[>+++<-]>.>>+++++++[>++++++<-]>++++.

在最低层次上,每种编程语言都是“相同的”,但这并不意味着它们在您实际交互的层次上是相同的。他们为您提取问题;这并不意味着他们抽象相同的问题或以相同的方式抽象每个问题。


1

成熟的语言通常有一些目标,并且会在权衡取舍时牺牲一件事为另一件事。通用语言可以用于任何事物,但是没有一种语言可以在每个领域都有出色的表现。一些例子:

C试图成为理想的系统编程语言。为此,它牺牲了可读性和低级控制和速度的安全性。

Python旨在成为理想的脚本语言。为此,它牺牲了速度和可验证性以提高生产率和便携性。

Haskell尝试成为一种安全的,数学上纯净的语言。为此,它牺牲了可学习性以及可验证性和可靠性的约定。

这些牺牲和好处在语言上产生了巨大的差异。是的,大多数编程语言都可以用于计算机可以完成的任何事情,但是这些相同的语言不能用于所有事情。以上所有语言都是我为某些任务选择的语言,而并非为其他任务选择的语言。如果要编写操作系统,则选择C。如果要编写网站的后端,则应使用Python。如果我正在编写金融系统,我会使用Haskell。

最后,您作为程序员的选择是正确的工作工具。

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.