First-class Everything

-- Guido van Rossum

First-class object: 第一类对象。意指可在执行期创建并作为参数传递给其他函数或存入一个变量的对象。

简而言之,第一类对象在使用时没有任何限制。第一类对象典型特征是可以动态创建、销毁,作为参数传递,可以作为返回值,具有一个变量的所具有的所有特性。

我关于Python的一个发展目标就是所有的对象都是第一类对象。鉴于此,我希望Python中的所有已命名的对象都具有相同的状态。也就是说,所有对象都可以赋值给变量,可以放进列表中,保存在字典里,作为参数传递等等。

Python的实现原理让这个目标变得简单。所有Python的对象都基于一个相同的C语言数据结构,这种结构充斥着Python解释器。变量、列表、函数等所有东西都使用这个数据结构的变体。这个数据结构与它要呈现的对象类型无关,无论是简单如整数,复杂如类都一样。

尽管实现第一类对象看起来简单,但我还是需要去面对类的一个微妙的地方——也就是,影响让method对象成为第一类对象的因素。

试看一个简单的Python类:

class A:
def __init__(self, x):
self.x = x
def spam(self, y):
print self.x, y

如果method对象成为第一类对象,那么它们就可以像其他Python对象一样被分配给变量。比如,某人可以写一条Python语句"s = A.spam"。此时,变量"s"指向一个类的方法,这个方法其实是个函数。但是,方法和普通的函数不同。方法的第一个参数应该是该定义了该方法的那个类的实例。

为解决这个问题,我创造了一种可调用对象"unbound method"。一个未绑定方法其实就是对实现该方法的函数的封装,它强制要求了它接收的第一个参数必须是定义了该方法的类的实例。因此,如果有人想像函数那样调用未绑定方法"s",他们只能将class A的一个实例作为第一个参数传递给"s"。就像"a = A(); s(a)"[注1]。

但随之带来一个问题,如果有人写了一条语句引用某个对象实例上的一个方法。比如,某人创建了一个实例"a = A()",然后写了另一条语句"s = a.spam"。此时,变量"s"再次指向一个类的方法,但是要引用这个方法需要通过instance对象"a"。为解决这个问题,另一个可调用对象"bound method"就派上用场了。这个对象也是对函数对象进行了一层简单封装。但是,这个封装对象隐式地保存了用来获取method的instance对象。因此,在执行"s()"时会隐式地将使用实例"a"作为第一个参数去调用目标方法。

实际上,bound和unbound方法都是使用同一种内部类型来呈现。该类型的对象有一个属性包含了指向某个实例的索引。如果该索引为None,那么它表示的就是unbound method,否则bound method。

尽管bound和unbound可能看起来不是很重要的小细节,但它们在Python类中却是很至关重要的一部分。每当在程序中执行"a.spam()"时,它的执行过程其实分为两部分。首先,查找"a.spam",这个过程结束后返回一个bound method——一个可调用对象;然后,对该对象使用函数调用符"()",从而使用用户提供的参数对方法进行调用。

[注1]在Python 3000中,unbound method的概念已去除,表达式"A.spam"返回一个函数对象。事实证明,对第一个参数必须是A的实例的限制对诊断问题几乎毫无帮助,对一些高级用法反而常常是个障碍。所谓高级用法可以理解为鸭子型态。

[Python] First-class Everything (Python缔造者Guido van Rossum关于bound/unbound method的来历叙述)的更多相关文章

  1. [Python] 当猎头遇上 Guido van Rossum

    Guido van Rossum 收到猎头的邀请函和他的回复. 猎头 你好,Guido! 我在 Google 搜索中无意间看见你的简历.看起来你精通 Python.我非常愉快能够得到你的回复并了解你的 ...

  2. [Python] Python 之 function, unbound method 和 bound method

    首先看一下以下示例.(Python 2.7) #!/usr/bin/env python # -*- coding: utf-8 -*- class C(object): def foo(self): ...

  3. 我的Python学习之路 Python的初识与准备工作

    注:文笔不好,不喜勿喷,当个段子看看就好 一.初识Python 第一次听到Python是在2016年大概暑假 时候(即将大三),因为对黑客技术的蜜汁热爱(虽然自己并不会),在玄魂大大的公众微信号中看到 ...

  4. Python之路(一)-python简介

    一.python简介,python2.x与python3.x的区别 Python是著名的“龟叔”Guido van Rossum在1989年圣诞节期间,为了打发无聊的圣诞节而编写的一个编程语言. Py ...

  5. JavaScript之父Brendan Eich,Clojure 创建者Rich Hickey,Python创建者Van Rossum等编程大牛对程序员的职业建议

    软件开发是现时很火的职业.据美国劳动局发布的一项统计数据显示,从2014年至2024年,美国就业市场对开发人员的需求量将增长17%,而这个增长率比起所有职业的平均需求量高出了7%.很多人年轻人会选择编 ...

  6. python学习笔记(python简史)

    一.python介绍 python的创始人为吉多·范罗苏姆(Guido van Rossum) 目前python主要应用领域: ·云计算 ·WEB开发 ·科学运算.人工智能 ·系统运维 ·金融:量化交 ...

  7. python基础之初始python

    初始python之基础一 一.Python 介绍 1.python的创始人为吉多·范罗苏姆(Guido van Rossum).1989年的圣诞节期间,吉多·范罗苏姆为了在阿姆斯特丹打发时间,决心开发 ...

  8. Python学习第一弹——Python环境搭建

    一.Python简介: Python,是一种面向对象.解释型计算机程序设计语言,由Guido van Rossum于1989年底发明,第一个公开发行版发行于1991年.Python语法简洁而清晰,具有 ...

  9. 进击的Python【第一章】:Python背景初探与Python基础(一)

    Python背景初探 一.Python起源 Python的创始人为Guido van Rossum.1989年圣诞节期间,在阿姆斯特丹,Guido为了打发圣诞节的无趣,决心开发一个新的脚本解释程序,做 ...

随机推荐

  1. mapreduce编程(一)-二次排序

    转自:http://blog.csdn.net/heyutao007/article/details/5890103 mr自带的例子中的源码SecondarySort,我重新写了一下,基本没变. 这个 ...

  2. 【Python】#!/usr/bin/python 作用

    脚本语言的第一行,目的就是指出,你想要你的这个文件中的代码用什么可执行程序去运行它 #!/usr/bin/python是告诉操作系统执行这个脚本的时候,调用/usr/bin下的python解释器.#! ...

  3. 第三百四十五节,Python分布式爬虫打造搜索引擎Scrapy精讲—爬虫和反爬的对抗过程以及策略—scrapy架构源码分析图

    第三百四十五节,Python分布式爬虫打造搜索引擎Scrapy精讲—爬虫和反爬的对抗过程以及策略—scrapy架构源码分析图 1.基本概念 2.反爬虫的目的 3.爬虫和反爬的对抗过程以及策略 scra ...

  4. 记一次艰难的IBM X3850重装系统和系统备份经验

    [贴心话] 刚刚把一切都搞定了,回到电脑前立马就写下的这篇文章,写的很细节,大家就耐心看看,有些细节是网上没有的,共享一下,仅供参考,以减少大家装机时遇到的困难. [面临处境] 机器型号:IBM X3 ...

  5. 系列篇:Python3.x那些事儿

    Python3.x那些事儿: http://jingyan.baidu.com/season/39306

  6. Linux入门教程:如何检查Linux系统的最后重启时间

    问题: 是否有一个命令可以快速地检查系统已经运行了多久? 也就是我怎么知道Linux系统最后的重启时间? 有许多方法来查询系统最后的重启时间. 方法一 第一种方法是使用last命令. $ last r ...

  7. springboot+shiro+redis(单机redis版)整合教程

    相关教程: 1. springboot+shiro整合教程 2. springboot+shiro+redis(集群redis版)整合教程 3.springboot+shiro+redis(单机red ...

  8. eclipse断点Source not found解决方案1,2,3

    1.tomcat插件 路径是Window --> Preferences --> Tomcat --> Source Path,在Source Path 标签下有行文字:Add ja ...

  9. .net网站建设页面提交后css失效的问题

    问题描述:.net网站建设在提交后出现css部分失效,如div位置,字体大小. 问题解决:原因是,过去的提示语句我们一律使用了Response.write("<script>al ...

  10. 【VirtualBox】共享文件夹失效问题

    fix: sudo ln -f -s /opt/VBoxGuestAdditions-5.1.20/lib/VBoxGuestAdditions/mount.vboxsf /sbin/mount.vb ...