专栏首页极客起源Python编程思想(19):可变参数也可以这样玩

Python编程思想(19):可变参数也可以这样玩

1. 为函数传递无限多个参数

很多编程语言都允许定义个数可变的参数,这样可以在调用函数时传入任意多个参数。Python当然也不例外,Python允许在形参前面添加一个星号(*),这样就意味着该参数可接收多个参数值,多个参数值被当成元组传入。下面程序定义了一个形参个数可变的函数。

示例代码:var_args.py

# 定义了支持可变参数的函数
def test(n, *books) :
    print(books)
    # books被当成元组处理
    for b in books :
        print(b)
    # 输出整数变量n的值
    print(n)
# 调用test()函数
test(10 , "Python从菜鸟到高手" , "Python爬虫")

运行上面程序,将看到如下运行结果:

('Python从菜鸟到高手', 'Python爬虫')
Python从菜鸟到高手
Python爬虫
10

从上面的运行结果可以看出,当调用 test()函数时,books参数可以传入多个字符串作为参数值。从 test()的函数体代码来看,可变参数的本质就是一个元组。Python会将传给 books参数的多个值放在一个元组里。

Python允许个数可变的形参可以处于形参列表的任意位置(不要求是形参列表的最后一个参数),但 Python要求一个函数最多只能带一个支持可变参数的形参。例子程序如下:

示例代码:var_args1.py

# 定义了支持参数收集的函数
def test(*books ,num) :
    print(books)
    # books被当成元组处理
    for b in books :
        print(b)
    print(num)
# 调用test()函数
test("Python从菜鸟到高手", "Android完全讲义", num = 123)

my_list = ["微信小程序开发入门精要", "Android权威指南"]
# 将列表的多个元素传给支持参数收集的参数
test(my_list, num = 120)
my_tuple= ("Python从菜鸟到高手", "Android完全讲义")
# 将元组的多个元素传给支持参数收集的参数
test(*my_tuple, num = 12)

运行这段代码,会输出下面的结果:

('Python从菜鸟到高手', 'Android完全讲义')
Python从菜鸟到高手
Android完全讲义
123
(['微信小程序开发入门精要', 'Android权威指南'],)
['微信小程序开发入门精要', 'Android权威指南']
120
('Python从菜鸟到高手', 'Android完全讲义')
Python从菜鸟到高手
Android完全讲义
12

正如从上面程序中所看到的,tes()函数的第1个参数就是个数可变的形参,由于该参数可接收个数不等的参数值,因此如果需要给后面的参数传入参数值,则必须使用关键字参数,否则,程序会把所传入的多个值都传给 books参数。Python还可以收集关键字参数,此时 Python会将这种关键字参数收集成字典。为了让 Python能收集关键字参数,需要在参数前面添加两个星号(**)。在这种情况下,一个函数可同时包含一个支持“普通”参数收集的参数和一个支持关键字参数收集的参数。例如如下代码

示例代码:var_args2.py

# 定义了支持参数收集的函数
def test(x, y, z=10, *books, **scores) :
    print(x, y, z)
    print(books)
    print(scores)
test(1, 2, 3, "Python从菜鸟到高手" , "Python爬虫", English=79, 高等数学=99)
test(4, 6, "Android完全开发讲义" , "Android权威指南", Chinese=97, 物理=68)
test(3, 7, 绘画=45, 音乐=78)

运行这段代码,会输出如下的内容:

1 2 3
('Python从菜鸟到高手', 'Python爬虫')
{'English': 79, '高等数学': 99}
4 6 Android完全开发讲义
('Android权威指南',)
{'Chinese': 97, '物理': 68}
3 7 10
()
{'绘画': 45, '音乐': 78}

对于上面代码中定义的 test()函数,参数z的默认值几乎不能发挥作用。比如按如下方式调用test()函数。

test(1,2,"Python从菜鸟到高手","Python爬虫",Chinese=90,Maths=100)

上面代码在调用 test()函数时,前面的1、2、"Python从菜鸟到高手"将会传给普通参数x、y、z,接下来的一个字符串将会由 books参数收集成元组。最后的两个关键字参数将会被收集成字典。运行上面代码,会看到如下输出结果。

1 2 Python从菜鸟到高手
('Python爬虫',)
{'Chinese': 90, 'Maths': 100}

如果希望让z参数的默认值发挥作用,则需要只传入两个位置参数。例如代码如下:

test(1,2,语文=90,数学=80)

上面代码在调用test()函数时,前面的1和2将会传给普通参数x、y,此时z参数将使用默认的参数值10, books参数将是一个空元组。接下来的两个关键字参数将会被收集成字典。运行上面代码,会看到如下输出结果。

1 2 10
()
{'语文': 90, '数学': 80}

2. 将集合拆成单个元素

将集合拆成单个元素,指的是在程序已有列表、元组、字典等对象的前提下,把它们的元素“拆开”后传给函数的参数。逆向参数收集需要在传入的列表、元组参数之前添加一个星号,在字典参数之前添加两个星号。

示例代码:var_args3.py

def test1(name, message):
    print(f"name: {name}")
    print(f"message: {message}")


my_list = ['雷神', '欢迎来到地球']
test1(*my_list)


def test2(name, *nums):
    print(f"name参数:{name}")
    print(f"nums参数: {nums}" )


my_tuple = (1, 2, 3)
# my_tuple元组的元素传给nums参数
test2('hello', *my_tuple)

# 将my_tuple元组的第1个元素传给name参数,剩下参数传给nums参数
test2(*my_tuple)

# my_tuple元组整体传给name参数
test2(my_tuple)


def test3(book, price, desc):
    print(book, f"price: {price}")
    print(f'desc:{desc}', desc)


my_dict = {'price': 128, 'book': 'Python从菜鸟到高手', 'desc': '这是一本全面介绍Python的书'}
# 将my_dict的多个key-value传给bar()函数
test3(**my_dict)

运行这段代码,会输出如下的结果:

name: 雷神
message: 欢迎来到地球
name参数:hello
nums参数: (1, 2, 3)
name参数:1
nums参数: (2, 3)
name参数:(1, 2, 3)
nums参数: ()
Python从菜鸟到高手 price: 128
desc:这是一本全面介绍Python的书 这是一本全面介绍Python的书

我们可以看到,如果不加星号(*),那么元组会被当做一个值传入函数,如果加星号(*),那么就会将该元组拆开,每一个元素都会作为独立的值传入函数。

本文分享自微信公众号 - 极客起源(geekculture),作者:geekori

原文出处及转载信息见文内详细说明,如有侵权,请联系 yunjia_community@tencent.com 删除。

原始发表时间:2020-06-16

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

我来说两句

0 条评论
登录 后参与评论

相关文章

  • Python从菜鸟到高手(1):初识Python

      Python是一种面向对象的解释型计算机程序设计语言,由荷兰人吉多·范罗苏姆(Guido van Rossum)于1989年发明,第一个公开发行版发行于19...

    蒙娜丽宁
  • 好消息,Python编程思想推出了!

    本系列文章深入介绍了Python的各种技术,堪称是目前最全的Python教程。主要目的是让读者可以了解Python的各种核心技术,包括各种Python函数库。本...

    蒙娜丽宁
  • Python从菜鸟到高手(2):清空Python控制台

    执行python命令会进入Python控制台。在Python控制台中可以用交互的方式执行Python语句。也就是执行一行Python语句,会立刻返回执行结果。

    蒙娜丽宁
  • 图像旋转

    描述 输入一个n行m列的黑白图像,将它顺时针旋转90度后输出。 输入第一行包含两个整数n和m,表示图像包含像素点的行数和列数。1 <= n <= 100,1 <...

    用户1631856
  • 【卷积神经网络失陷】几行Python代码搞定,偏要用100个GPU!

    【新智元导读】Uber近日一篇论文引起许多讨论:该论文称发现卷积神经网络一个引人注目的“失败”,并提出解决方案CoordConv。论文称CoordConv解决了...

    新智元
  • 斯坦福CS231N深度学习与计算机视觉第二弹:图像分类与KNN

    大数据文摘
  • 计算机芯片重大漏洞被发现,可能缩短芯片使用寿命

    美国华盛顿州立大学的一个研究小组发现,高性能计算机芯片中存在重大的、此前未知的漏洞,这些漏洞可能导致现代电子产品出现故障。

    AiTechYun
  • ELK分析ngx_lua_waf软件防火墙日志

    https://github.com/loveshell/ngx_lua_waf

    三杯水Plus
  • 前端常用PS技巧总结之更换图片背景图片

    嗯,今天我们接着写关于前端试用技巧部分的如果将任务背景图片更换掉,为什么写这个呢?在上一篇文章的时候我说图片变的透明是很重要的一件事情,那么其实很多的时候啊我们...

    何处锦绣不灰堆
  • 零基础学习Python应该掌握哪些知识点?

    Python现在非常火,语法简单而且功能强大,很多同学都想学Python!所以小的给各位看官们准备了高价值Python学习视频教程及相关电子版书籍,欢迎前来领取...

    python学习教程

扫码关注云+社区

领取腾讯云代金券