为了账号安全,请及时绑定邮箱和手机立即绑定

如何执行函数列表并将数据传递给使用 asyncio 调用的适当函数

如何执行函数列表并将数据传递给使用 asyncio 调用的适当函数

九州编程 2021-06-08 13:58:37
我以前使用过请求,但后来我转向 aiohttp + asyncio 来并行运行帐户,但是我无法将逻辑放在我的脑海中。class Faked(object):    def __init__(self):        self.database = sqlite3.connect('credentials.db')    async def query_login(self, email):        print(email)        cur = self.database.cursor()        sql_q = """SELECT * from user WHERE email='{0}'""".format(email)        users = cur.execute(sql_q)        row = users.fetchone()        if row is None:            raise errors.ToineyError('No user was found with email: ' + email + ' in database!')        self.logger().debug("Logging into account '{0}'!".format(row[0]))        call_func = await self._api.login(data={'email': row[0],                                                'password': row[1],                                                'deviceId': row[2],                                                'aaid': row[3]})        return await call_func    async def send_friend_request(self, uid):        return await self._api.send_friend_request(uid)def main(funcs, data=None):    """   todo: fill  :rtype: object  """    tasks = []    if isinstance(funcs, list):        for func in funcs:            tasks.append(func)    else:        tasks.append(funcs)    print(tasks)    loop = asyncio.get_event_loop()    results = loop.run_until_complete(asyncio.gather(*tasks))    for result in results:        print(result)    return resultsif __name__ == '__main__':  # for testing purposes mostly    emails = ['email@hotmail.com', 'email@outlook.com', 'email@gmail.com']我基本上只是想知道如何对多个函数进行排队,在这种情况下,query_login 和 send_friend_request,同时还将正确的数据传递给上述函数,假设我同时在一个社交媒体应用程序上运行三个帐户,这真的让我大吃一惊,虽然我有使事情过于复杂的倾向,但任何帮助将不胜感激。
查看完整描述

2 回答

?
吃鸡游戏

TA贡献1829条经验 获得超7个赞

Python 旨在通过解包运算符 * 或使用 lambda 使这变得相当容易

让我们来看看吧。


callstack = [] # initialize a list to serve as our stack.

     # See also collections.deque for a queue.

然后我们可以定义我们的函数:


def somefunc(a, b, c): 

    do stuff...

然后将参数作为列表添加到堆栈中。


args = [a, b, c]

callstack.append((somefunc, args)) # append a tuple with the function

            # and its arguments list.


# calls the next item in the callstack

def call_next(callstack):

    func, args = callstack.pop() # unpack our tuple

    func(*args) # calls the func with the args unpacked

* 运算符将您的列表解包并按顺序提供它们作为参数。您还可以使用双星运算符 (**) 解压缩关键字参数。


def call_next(callstack):

    func, args, kwargs = callstack.pop() # unpack our tuple

    func(*args, **kwargs) # calls the func with both args and kwargs unpacked.

另一种方法是创建一个 lambda。


def add(a, b):

    return a + b


callstack = []


callstack.append(lambda: add(1, 2))

callstack.pop()() # pops the lambda function, then calls the lambda function, 

                  # which just calls the function as you specified it.

瞧!所有功劳都归功于另一个线程中的作者。这里有一个问题:如果您将对象作为参数传递,它将作为引用传递。请小心,因为您可以在堆栈中调用对象之前对其进行修改。


def add(a, b, c):

    return a + b + c


badlist = [1,2,3]

callstack.append((somefunc, badlist))

badlist = [2, 4, 6]

callstack.append((somefunc, badlist))


while len(callstack) > 0:

    print(call_next(callstack))


# Prints:

12

12

你可以在 *args 版本中解决这个问题:


# make a shallow copy and pass that to the stack instead.

callstack.append((somefunc, list(badlist))) 

在 lambda 函数中,整个事物都在调用时进行评估,因此即使通常不是引用的事物也表现得像引用。上述技巧不起作用,因此在创建 lambda 之前根据需要进行任何复制。


查看完整回答
反对 回复 2021-06-29
  • 2 回答
  • 0 关注
  • 151 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
微信客服

购课补贴
联系客服咨询优惠详情

帮助反馈 APP下载

慕课网APP
您的移动学习伙伴

公众号

扫描二维码
关注慕课网微信公众号