美文网首页
刨根问底:对象也可以当方法用?

刨根问底:对象也可以当方法用?

作者: 丹枫无迹 | 来源:发表于2019-04-26 14:34 被阅读0次

1、问题

我刚开始接触爬虫的时候,只是看完了 python 的基础,对 python 的语法还没有一个很深入的了解,在使用 bs4 这个库的时候,对其中某些语法感到非常的惊奇,不明白是怎么实现的。

bs4 的官方文档中说到:find_all() 几乎是 Beautiful Soup 中最常用的搜索方法,所以我们定义了它的简写方法。BeautifulSoup 对象和 tag 对象可以被当作一个方法来使用,这个方法的执行结果与调用这个对象的 find_all() 方法相同,下面两行代码是等价的:

soup.find_all("a")
soup("a")

这里,soup 是一个 BeautifulSoup 对象,soup("a") 这很明显是把对象当方法使用了,这是怎么做到的呢?

2、实现

在 Python 中,除了用户定义的函数,调用运算符(即 ())还可以应用到其他对象上。内置的 callable() 函数用来判断一个对象能否调用。就是说,任何 Python 对象都可以表现得像函数一样,为此,只需实现实例方法 __call__

来看一个简单的示例:

class Sum:
    def __init__(self, x, y):
        self._x = x
        self._y = y

    def add(self):
        return self._x + self._y

    def __call__(self):
        return self.add()


sum = Sum(1, 2)

print(sum.add())
print(sum())
print(callable(sum))

输出:

3
3
True

这样就明白了,bs4 中亦是如此,源码如下:

class Tag(PageElement):
    def __call__(self, *args, **kwargs):
        return self.find_all(*args, **kwargs)

这背后涉及到的概念叫做可调用对象,Python 数据模型文档列出了 7 种可调用对象。

  • 用户定义的函数:使用 def 语句或 lambda 表达式创建。
  • 内置函数:使用 C 语言(CPython)实现的函数,如 len 或 time.strftime。
  • 内置方法:使用 C 语言实现的方法,如 dict.get。
  • 方法:在类的定义体中定义的函数。
  • :调用类时会运行类的 \__new__ 方法创建一个实例,然后运行 \__init__ 方法,初始化实例,最后把实例返回给调用方。因为 Python 没有 new 运算符,所以调用类相当于调用函数。(通常,调用类会创建那个类的实例,不过覆盖 \__new__ 方法的话,也可能出现其他行为。)
  • 类的实例:如果类定义了 \__call__ 方法,那么它的实例可以作为函数调用。
  • 生成器函数:使用 yield 关键字的函数或方法。调用生成器函数返回的是生成器对象。

相关文章

  • 刨根问底:对象也可以当方法用?

    1、问题 我刚开始接触爬虫的时候,只是看完了 python 的基础,对 python 的语法还没有一个很深入的了解...

  • 对象也可以当方法用?

    1、问题 我刚开始接触爬虫的时候,只是看完了 python 的基础,对 python 的语法还没有一个很深入的了解...

  • Range对象和Selection对象

    Range可以用 Document 对象的 createRange方法创建,也可以用Selection对象的get...

  • 13.JavaScript类数组

    类数组 有下标,有length,有push和splice,就是一个类数组 既可以当数组用,也可以当对象用。 DOM...

  • OKHTTP

    OKHTTP流程: 初始化OkHttpClient对象,在构造方法里面用默认的Builder对象进行初始化,也可以...

  • Vue-class与s'tyle绑定

    一、 用对象的方法绑定class 说明设置一个对象,可以动态地切换class对象中也可以传入多个属性,来动态切换c...

  • 匿名

    匿名对象使用方式一:当对对象的方法只调用一次时,可以用匿名对象来完成,这样写比较简化。如果对一个对象进行多个成员调...

  • javascript中的面向对象编程笔记

    创建object对象 在javascript中,创建object的方法有几种,可以直接用“{}”创建 也可以利用构...

  • Java入门教程:java基础基本语法是什么?

    当考虑Java程序也可以被定义为通过调用对方的方法,该通信对象的集合。现在,让我们简要地看到什么类,对象,方法和实...

  • 想搞懂async?先从单向链表讲起

    async怎么用 async函数返回一个Promise对象,可以使用then方法添加回调函数。当函数执行的时候,一...

网友评论

      本文标题:刨根问底:对象也可以当方法用?

      本文链接:https://www.haomeiwen.com/subject/jmdbwqtx.html