python中前缀运算符 *和 **的用法示例详解
这篇主要探讨**和*前缀运算符,**在变量之前使用的*and**运算符.
一个星(*):表示接收的参数作为元组来处理
两个星(**):表示接收的参数作为字典来处理
简单示例:
>>>numbers=[2,1,3,4,7] >>>more_numbers=[*numbers,11,18] >>>print(*more_numbers,sep=',') 2,1,3,4,7,11,18
用途:
- 使用*和**将参数传递给函数
- 使用**和**捕获传递给函数的参数
- 使用*只接受关键字参数
- 使用*元组拆包过程中捕获项目
- 使用*解包iterables到一个列表/元组
- 使用**要解压缩词典到其他字典
例子解释:
1.调用函数时,*可以使用运算符将可迭代对象解压缩为函数调用中的参数:
>>>fruits=['lemon','pear','watermelon','tomato'] >>>print(fruits[0],fruits[1],fruits[2],fruits[3]) lemonpearwatermelontomato >>>print(*fruits) lemonpearwatermelontomato
该print(*fruits)行将fruits列表中的所有项目print作为单独的参数传递到函数调用中,而我们甚至不需要知道列表中有多少个参数。
2.**运算符允许我们采取键值对的字典,并把它解压到函数调用中的关键字参数。
>>>date_info={'year':"2020",'month':"01",'day':"01"} >>>filename="{year}-{month}-{day}.txt".format(**date_info) >>>filename '2020-01-01.txt'
**将关键字参数解包到函数调用中并不是很常见。我最常看到的地方是练习继承时:super()通常要同时包含*和**。
双方*并**可以在函数调用中多次使用,像Python3.5的。
>>fruits=['lemon','pear','watermelon','tomato'] >>>numbers=[2,1,3,4,7] >>>print(*numbers,*fruits) 21347lemonpearwatermelontomato **多次使用类似: >>>date_info={'year':"2020",'month':"01",'day':"01"} >>>track_info={'artist':"Beethoven",'title':'SymphonyNo5'} >>>filename="{year}-{month}-{day}-{artist}-{title}.txt".format( ...**date_info, ...**track_info, ...) >>>filename '2020-01-01-Beethoven-SymphonyNo5.txt'
3.定义函数时,*可以使用运算符捕获为函数提供的无限数量的位置参数。这些参数被捕获到一个元组中。
fromrandomimportrandint defroll(*dice): returnsum(randint(1,die)fordieindice
4.我们可以用**定义一个函数时,捕捉给予功能到字典中的任何关键字参数:
deftag(tag_name,**attributes): attribute_list=[ f'{name}="{value}"' forname,valueinattributes.items() ] returnf"<{tag_name}{''.join(attribute_list)}>"
5.带有仅关键字参数的位置参数,要接受仅关键字的参数,可以*在定义函数时在使用后放置命名参数
defget_multiple(*keys,dictionary,default=None): return[ dictionary.get(key,default) forkeyinkeys ] 上面的函数可以这样使用: >>>fruits={'lemon':'yellow','orange':'orange','tomato':'red'} >>>get_multiple('lemon','tomato','squash',dictionary=fruits,default='unknown') ['yellow','red','unknown']
参数dictionaryanddefault在其后*keys,这意味着只能将它们指定为关键字参数。如果我们尝试在位置上指定它们,则会收到错误消息:
>>>fruits={'lemon':'yellow','orange':'orange','tomato':'red'} >>>get_multiple('lemon','tomato','squash',fruits,'unknown') Traceback(mostrecentcalllast): File"",line1,in TypeError:get_multiple()missing1requiredkeyword-onlyargument:'dictionary'
6.不带位置参数的仅关键字参数
仅关键字参数的功能很酷,但是如果您需要仅关键字参数而不捕获无限的位置参数怎么办?
defwith_previous(iterable,*,fillvalue=None): """Yieldeachiterableitemalongwiththeitembeforeit.""" previous=fillvalue foriteminiterable: yieldprevious,item previous=item ```
该函数接受一个iterable参数,该参数可以在位置上指定(作为第一个参数),也可以通过其名称和作为fillvalue仅关键字参数的参数来指定。这意味着我们可以这样调用with_previous:
>>>list(with_previous([2,1,3],fillvalue=0)) [(0,2),(2,1),(1,3)] 但不是这样的: >>>list(with_previous([2,1,3],0)) Traceback(mostrecentcalllast): File"",line1,in TypeError:with_previous()takes1positionalargumentbut2weregiven 此函数接受两个参数,并且其中一个fillvalue必须指定为关键字arguments。
7.元组拆包中的星号
Python3还添加了一种新的使用运算符的方式,该方式仅与上面的-when-defining-a-function和*-when-when-calling-afunction功能有关。
>>>fruits=['lemon','pear','watermelon','tomato'] >>>first,second,*remaining=fruits >>>remaining ['watermelon','tomato'] >>>first,*remaining=fruits >>>remaining ['pear','watermelon','tomato'] >>>first,*middle,last=fruits >>>middle ['pear','watermelon']
8.列表文字中的星号
Python3.5通过PEP448引入了大量的新功能。最大的新功能之一是能够将可迭代对象转储到新列表中。
假设您有一个函数,该函数可以接收任何序列,并返回一个列表,其中该序列与该序列的反序连接在一起:
defpalindromify(sequence): returnlist(sequence)+list(reversed(sequence))
该函数需要将事物转换为列表几次,以连接列表并返回结果。在Python3.5中,我们可以改为输入:
defpalindromify(sequence): return[*sequence,*reversed(sequence)]
此代码删除了一些不必要的列表调用,因此我们的代码更加高效和可读。
这是另一个例子:
defrotate_first_item(sequence): return[*sequence[1:],sequence[0]]
该函数返回一个新列表,其中给定列表(或其他序列)中的第一项移动到新列表的末尾。
*运算符的这种使用是将不同类型的可迭代对象连接在一起的好方法。的*操作者适用于任何可迭代,而使用+操作者仅适用于具有所有相同类型的特定序列。
这不仅限于创建列表。我们还可以将可迭代项转储到新的元组或集合中:
>>>fruits=['lemon','pear','watermelon','tomato'] >>>(*fruits[1:],fruits[0]) ('pear','watermelon','tomato','lemon') >>>uppercase_fruits=(f.upper()forfinfruits) >>>{*fruits,*uppercase_fruits} {'lemon','watermelon','TOMATO','LEMON','PEAR','WATERMELON','tomato','pear'}
请注意,上面的最后一行获取一个列表和一个生成器,并将它们转储到新集中。在使用之前*,以前没有一种简单的方法可以在一行代码中做到这一点。以前有一种方法可以做到,但要记住或发现它并不容易:
>>>set().union(fruits,uppercase_fruits) {'lemon','watermelon','TOMATO','LEMON','PEAR','WATERMELON','tomato','pear'}
9.字典文字中的双星号
PEP448还**允许该运算符用于将键/值对从一个字典转储到新字典中,从而扩展了功能:
>>>date_info={'year':"2020",'month':"01",'day':"01"} >>>track_info={'artist':"Beethoven",'title':'SymphonyNo5'} >>>all_info={**date_info,**track_info} >>>all_info {'year':'2020','month':'01','day':'01','artist':'Beethoven','title':'SymphonyNo5'}
例如,我们可以在添加新值的同时复制字典:
>>>date_info={'year':'2020','month':'01','day':'7'} >>>event_info={**date_info,'group':"PythonMeetup"} >>>event_info {'year':'2020','month':'01','day':'7','group':'PythonMeetup'}
或在覆盖特定值的同时复制/合并字典:
>>>event_info={'year':'2020','month':'01','day':'7','group':'PythonMeetup'} >>>new_info={**event_info,'day':"14"} >>>new_info {'year':'2020','month':'01','day':'14','group':'PythonMeetup'}
ref:https://treyhunner.com/2018/10/asterisks-in-python-what-they-are-and-how-to-use-them/
总结
到此这篇关于python中前缀运算符*和**的用法示例详解的文章就介绍到这了,更多相关python中*和**的用法内容请搜索毛票票以前的文章或继续浏览下面的相关文章希望大家以后多多支持毛票票!
声明:本文内容来源于网络,版权归原作者所有,内容由互联网用户自发贡献自行上传,本网站不拥有所有权,未作人工编辑处理,也不承担相关法律责任。如果您发现有涉嫌版权的内容,欢迎发送邮件至:czq8825#qq.com(发邮件时,请将#更换为@)进行举报,并提供相关证据,一经查实,本站将立刻删除涉嫌侵权内容。