何时在编程语言/平台中将某个功能视为“头等公民”?


61

我已经看过很多次声明,例如-“请在某种语言/平台中使此功能成为一流的公民”。例如,关于C#/。net中的枚举的说法。那么,在编程语言/平台中,什么时候将某个功能视为“一流公民”?

Answers:


40

定义

对象在以下情况下是一流的:

  • 可以存储在变量和数据结构中
  • 可以作为参数传递给子例程
  • 可以作为子例程的结果返回
  • 可以在运行时构造
  • 具有固有身份(与任何给定名称无关)

术语“对象”在这里被宽松地使用,不必在面向对象的编程中指代对象。最简单的标量数据类型(例如整数和浮点数)几乎总是一流的。

http://en.wikipedia.org/wiki/First_class_object


1
那么,是什么让.net / C#中的枚举第二类对象呢?
Gulshan

7
@Gulshan-您可以争辩缺乏内在身份-C#枚举基本上只是整数值的语法糖(即“给定名称”)。与Java相比,枚举本身就是对象。
mikera 2011年

.mi枚举中的@mikera本身就是值。Java只是没有任何值,只有对象,这是唯一的区别。
SK-logic

@mikera:尽管这阻止了Java枚举具有一些不错的属性,例如能够用它们表示位字段。尽管它们的实现可能是一流的,但大多数API仍具有大量的整数(或字符串)常量,并且这些常量的许多用法无法轻松地用枚举代替。
乔伊,

我不认为可以在.Net的运行时中构造枚举,可以吗?我以为它们总是常数。
travis

33

编程语言中的“一流公民”或“一流元素”的概念是由英国计算机科学家克里斯托弗·斯特拉奇Christopher Strachey)于1960年代在一流功能的背景下提出的。该原理最著名的提法可能是杰拉尔德·杰伊·萨斯曼和哈里·阿贝尔森的《计算机程序结构和解释》

  • 它们可以用变量命名。
  • 它们可以作为参数传递给过程。
  • 它们可能作为程序的结果返回。
  • 它们可能包含在数据结构中。

基本上,这意味着您可以使用该编程语言元素来完成您可以使用该编程语言中的所有其他元素来进行的所有操作。

这一切都是关于“平等权利”的:您可以用整数来完成上述所有工作,那么为什么其他任何东西都应该有所不同呢?

上面的定义在某种意义上是有限制的,因为它仅真正涉及与作为程序对象有关的一流性。一个更笼统的定义是,如果您可以用一件事情做所有事情,那么您也可以用其他同类的事情做一件一流的事情。

例如,Java运算符和Java方法是类似的类型。您可以定义新方法,可以(某种程度上)自由选择自己方法的名称,可以覆盖方法,可以重载方法。詹姆斯·高斯林(James Gosling)也可以通过操作员来完成所有这些工作,但是您和我却做不到。我的意思是,流行的看法相反,Java的支持运算符重载:例如,+运营商目前超载byteshortintlongfloatdoubleString,和IIRC Java 7中也BigIntegerBigDecimal(也许几个我忘了),它只是对它没有任何影响。显然,这使操作员根据第二个定义成为第二等。请注意,根据第一个定义,方法仍然不是一流的对象。(这使操作员成为第三流吗?)


6

通常,这是指可以作为参数传递,可以定义为函数的返回类型或可以分配值的构造。通常,您需要能够在运行时构造它们。例如,一个类的实例在c ++或java中将是一等公民,而在C中的函数则不是。


是什么使一类成为c ++中的一等公民?
Bjarke Freund-Hansen

2
@bjarkef:听起来已经通过与前面句子中提供的描述相匹配来回答。
doppelgreener 2011年

@Jonathan:是的,很抱歉,我误读了“在运行时构造它们”。是的,您可以在运行时构造一个类的实例(一个对象),但是不能构造类本身。那就是让我困惑的地方。
Bjarke Freund-Hansen

1
仅通过参数传递还不够。在C / C ++中,我仍将函数视为二等公民。可以将它们作为参数传递,并作为结果放入其他对象中。但是,如果没有其他构造的帮助,就无法对其进行操作(例如,需要std :: bind才能将参数绑定到函数)。
马丁·约克

@Martin我从未说过函数是C / C ++中的一等公民。
Pemdas 2011年

1

我想说的是,如果仅通过语言实现某项功能,则它就是一流的公民。
也就是说,它不需要多种语言功能或标准库即可实现该功能。

例:

在C / C ++中,我不认为函数是一等公民(其他人可能是)。
这是因为有一些方法可以操纵语言直接支持的功能,但需要使用其他语言功能。不直接支持将参数绑定到函数,并且您必须构建函子才能实现此功能。


1
难道使绑定的函数(或“闭包”)不是一流的,而函数本身却是一流的?0x对闭包的支持如何影响您的分析?
Fred Nurk 2011年

@Fred Nurk:这完全取决于语言。在某些语言中,闭包是一流的系统。在其他人没有。我对C ++ 0x不够熟悉,无法做出明确的评论。
马丁·约克

假设您回答中的语言是C或C ++(但不是0x)。您对“一流”的定义是否会使绑定的函数(或“封闭”)不是一流,而函数本身却是一流的呢?
弗雷德·努克

@Fred Nurk:如果您限制使用函数的唯一操作就是将它们设置为闭包,那么可以确定。但是对我来说,这就像说您的平台是否仅通过导入库来支持整数加法。然后,整数是一等公民,但不考虑整数的加法。在我看来,闭包是可以在有效地返回新函数的函数上执行的操作(但这取决于您如何定义它)。但是闭包和绑定只是我们要从讨论中排除的其他两个操作(我不确定这是一个问题)。
马丁·约克

@马丁:我一定不能清楚地解释自己。给定“如果某项功能仅通过语言实现,则该功能为一等公民”,那么C和C ++中的功能均仅通过该语言实现,因此将是一流的。绑定函数(也可以称为“闭包”)是您在使用绑定参数等时要说的,但这是一个不同的功能。
Fred Nurk,2011年

-1

要将示例添加到已经提供的答案中:

在WCF / C#中,您当前必须使用服务协定属性标记一个类对象,以使其作为服务运行。没有这样的事情:

public **service** MyService (in relation public **class** MyClass). 

类是c#中的一等公民,而c#中没有服务。

希望这可以帮助

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.