【问题标题】:Passing a member function as a function arg?将成员函数作为函数 arg 传递?
【发布时间】:2012-06-07 08:08:13
【问题描述】:

我为 SQLite 编写了一个非常简单的选择函数,但我对如何传递成员函数感到困惑……例如:.fetchone().fetchmany()

def select(cursor, select="*", table="reuters", fetch=".fetchone()", tologfile=False, logfile=""):
    if tologfile:
        logfile = open(logfile, 'w')
        logfile.write(str(cursor.execute("select * from ?;".replace('?',table).replace("select * ", "select "+select)).fetchone()))
        logfile.close()
    else: return str(cursor.execute("select * from ?;".replace('?',table).replace("select * ", "select "+select)).fetchone())

如何将此成员函数作为 arg 传递?

【问题讨论】:

    标签: python sqlite select functional-programming pysqlite


    【解决方案1】:

    您可以简单地传递self.fetchone 来传递该函数。

    如果您希望它作为默认值,只需在函数定义中使用 None 并添加

    if whatever is None:
        whatever = self.fetchone
    

    在函数本身中。

    如果您想在另一个对象上调用该方法,但 self 继续将其作为字符串传递并使用此代码(基于您的 else 代码,因为该代码更短):

    result = self.execute("select * from ?;".replace('?',table).replace("select * ", ("select "+attr)))
    return str(getattr(result, whatever)())
    

    【讨论】:

    • 啊,您想在查询中的对象上调用该方法..误解了您的问题
    • 别担心,期待阅读您修改后的答案:)
    • 为什么不传递未绑定的方法(Class.method)并调用它,将所需的实例作为第一个参数传递?无需将方法名称作为字符串传递。
    【解决方案2】:

    你可以使用 getattr :

    >>> class A:
    ...     def b(self):
    ...             print 'c'
    ... 
    >>> a = A()
    >>> getattr(a,'b')
    <bound method A.b of <__main__.A instance at 0x7f2a24a85170>>
    >>> getattr(a,'b')()
    c
    

    【讨论】:

      【解决方案3】:

      一个 lambda 可以做到这一点

      class A:
        def test(self):
          print "hello world"
      
      a = A()
      func = (lambda: a.test())
      func()
      

      打印“hello world”

      此技术也可以扩展为处理传递和转换参数

      class B:
        def test(self, x):
          print x
      
      b = B()
      func = (lambda a, b : b.test(b))
      func("garbage", "foo")
      

      打印“foo”

      【讨论】:

      • 或者,您可以只使用func = a.test。 lambda 是不必要的。
      【解决方案4】:

      好的,开始工作了:

      import sqlite3
      
      def select(self, attr="*", table="reuters", fetch=None, num=None, tologfile=False, logfile=""):
          if fetch is None:
              fetch=self.fetchone
          output=self.execute("select * from ?;".replace('?',table).replace("select * ", ("select "+attr+' ')))
      
          output=fetch(num) if num else fetch()
      
          if tologfile:
              logfile = open(logfile, 'w')
              logfile.write(str(output))
              logfile.close()
          else: return output
      
      if __name__ == '__main__':    
          connection = sqlite3.connect('winkwinknudgenudgesaynomore.db')
          cursor = connection.cursor()
          cursor.execute("drop table reuters;")
          cursor.execute("create table reuters (foo text, bar text);")
          connection.commit()
          print select(cursor)
          print select(cursor, 'bar')
          print select(cursor, 'bar', fetch=cursor.fetchmany, num=5)
          cursor.close()
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2019-09-27
        • 1970-01-01
        • 2013-06-29
        • 2018-09-18
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2016-09-11
        相关资源
        最近更新 更多