## 函数
  - 函数是代码的一种组织形式,一般一个函数完成一个特定功能
  - 函数需要先定义后使用

  - 函数的定义

    def func_name(参数):
      func_body
      ...
      return func_result

## 函数的返回值
  - 函数和过程的区别就在于有没有返回值
  - 用return关键字表示返回内容
  - 函数内在执行到return语句后,整个函数无条件结束执行
  - 若在函数定义时没有明确的写明return内容,则该函数默认返回None
  - 推荐无论函数有没有返回值都以return结束

## 函数的参数

  - 位置参数(positional argument)
    - 参数的值按照顺序依次传递
    - 最常见,但是必须牢记每个位置参数的含义,若位置混淆,将会得到不可预测的结果

    def self_intro(name, age, love):
  return "Hello, I'm {0}, {1} years old, I love {2}".format(name, age, love)     self_intro("Stanley", 22, "Python")
    # "Hello, I'm Stanley, 22 years old, I love Python"

    - 若参数位置错误,将会得到意外的结果

    self_intro(22, "Stanley", "Python")
    # "Hello, I'm 22, Stanley years old, I love Python"

  - 关键字参数(keyword argument)
    - 在函数调用时使用关键字,明确每个参数对应的值,以避免位置参数带来的混乱

    self_intro(age=22, name="Stanley", love="Python")
    # "Hello, I'm Stanley, 22 years old, I love Python"

    - 也可以将位置参数和关键字参数结合使用,此时位置参数位置必须对应,关键字参数位置可以不对应

    self_intro("Stanley", love="Python", age=22)
    # "Hello, I'm Stanley, 22 years old, I love Python"

  - 默认参数
    - 无论是关键字参数还是位置参数,在函数调用时都必须提供参数值
    - 对于不常用的参数或者多次函数调用使用相同值的参数就可以使用默认值参数,在函数调用时若未指定该参数的值,则该参数使用默认值,若指定了参数值则使用指定值

    def self_intro(name, age, love="Python"):
    return "Hello, I'm {0}, {1} years old, I love {2}".format(name, age, love)     self_intro("Stanley", 22)
    # "Hello, I'm Stanley, 22 years old, I love Python"     self_intro("Stanley", 22, love="Lily")
    # "Hello, I'm Stanley, 22 years old, I love Lily"

    - 默认参数在函数被定义的时候就已经计算出来,而不是在程序运行的时候计算,所以在将可变的数据类型(比如列表或字典)当做默认参数时会出现一些问题

    def demo(num, result=[]):
     """
     将第一个参数添加到列表中,并返回一个单值列表
       """
     result.append(num)
     return result     demo(1) # 函数第一次调用没有问题
    # [1]     demo(2)   # 预期返回[2]
    # [1, 2] # 实际返回

    原因分析:默认参数在定义的时候就已经计算出来结果,之后的多次调用都只是针对原有列表进行操作,并没有生成新的列表,所以结果与预期有差异

    修改:

    def demo(num):
     result = [] # 此时每次函数调用都生成一个新的列表
     result.append(num)
     return result     demo(1)
    # []     demo(2)
    # [2] # 结果与预期相同

    或:

    def demo(num, result=None):
     if result is None: # 若函数在调用时没有设置默认参数,则生成新的空列表
     result = []
     result.append(num)
     return result     demo(1)
    # []     demo(2)
    # []     demo(3, result=[1, 2])
    # [1, 2, 3]     demo(4)
    # [4]

  - 收集参数
    - 收集参数有两种,分别使用*收集位置参数,使用**收集关键字参数

    - 使用*收集位置参数
    - 当参数被用在函数内部时,*将一组可变数量的位置参数收集添加到一个元组中
    

    def get_args(*args):
     return args     get_args(1, 2, 3, "a", "b")
    # (1, 2, 3, 'a', 'b')

    - 位置参数和*收集参数同时使用,位置参数在获取值后,将其余位置参数全部放入*收集参数中      

    def self_intro(name, age, *loves):
     return "Hello, I'm {0}, {1} years old. I love {2}".format(name, age, loves)     self_intro("Stanley", 22, "Python", "JS", "HTML", "CSS")
    # "Hello, I'm Stanley, 22 years old. I love ('Python', 'JS', 'HTML', 'CSS')"

    - 使用**收集关键字参数
      - 使用**可以将参数收集到一个字典中,参数的名称是字典的键,对应的参数值是字典的值

    def self_intro(**kwargs):
     return kwargs     self_intro(name="Stanley", age=22, love="Python")
    # {'name': 'Stanley', 'age': 22, 'love': 'Python'}

  - 几种参数的混合使用

    def self_intro(name, age, *args, love="Python", **kwargs):
     print("My name is {0}, I'm {1} years old".format(name, age))
     for arg in args:
     print("I'm {}".format(arg))
     print("My love is {0}".format(love))
     for k, v in kwargs.items():
     print("My {0} is {1}".format(k, v))     self_intro("Stanley", 22, "male", "Student", nationality="China", major="English")
    # My name is Stanley, I'm 22 years old
    # I'm male
    # I'm Student
    # My love is Python
    # My nationality is China
    # My major is English

## 函数递归
  - 函数自己调用自己
  - 优点:简洁,容易理解
  - 缺点:对递归深度有限制,消耗资源大
  - 写递归时一定注意结束条件,递归次数不要超过python系统限制

  - fibnacci数列

 def fib(n):
lis = []
for i in range(n):
if i == 0 or i == 1:
lis.append(1)
else:
lis.append(lis[i - 1] + lis[i - 2])
return lis def f(n):
if n == 1 or n == 2:
return 1
return f(n - 1) + f(n - 2) print(f(10)) # -> 55
print(fib(10)) # -> [1, 1, 2, 3, 5, 8, 13, 21, 34, 55]

## 函数文档
  - 函数的文档的作用是对当前函数提供使用相关的参考信息
  - 文档的写法
      - 在函数内部开始的第一行使用三双引号字符串定义符
      - 一般具有特定格式
  - 文档查看
    - 使用help(func_name)
    - 使用func_name.__doc__

本文参考书籍:[美]Bill Lubanovic 《Python语言及其应用》

Python函数及参数的更多相关文章

  1. Python函数可变参数*args及**kwargs详解

    初学Python的同学们看到代码中类似func(*args, **kwargs)这样的函数参数定义时,经常感到一头雾水. 下面通过一个简单的例子来详细解释下Python函数可变参数*args及**kw ...

  2. 【转】Python函数默认参数陷阱

    [转]Python函数默认参数陷阱 阅读目录 可变对象与不可变对象 函数默认参数陷阱 默认参数原理 避免 修饰器方法 扩展 参考 请看如下一段程序: def extend_list(v, li=[]) ...

  3. 详解python函数的参数

    详解python函数的参数 一.参数的定义 1.函数的参数在哪里定义 在python中定义函数的时候,函数名后面的括号里就是用来定义参数的,如果有多个参数的话,那么参数之间直接用逗号, 隔开 案列: ...

  4. 可变数据类型不能作为python函数的参数

    可变数据类型:列表.字典 不可变数据类型:整型.浮点型.字符串.元组 为什么可变数据类型不能作为python函数的参数?请看以下例子: def foo(a=[]): a.append(1) retur ...

  5. python 函数传递参数的多种方法

    python中函数根据是否有返回值可以分为四种:无参数无返回值,无参数有返回值,有参数无返回值,有参数有返回值. Python中函数传递参数的形式主要有以下五种,分别为位置传递,关键字传递,默认值传递 ...

  6. python函数动态参数详解

    Python的动态参数: 1,参数前一个"*":在函数中会把传的参数转成一个元组. def func (*args): print(args) func(123,1,2,'a') ...

  7. Python 函数的参数知识汇总

    函数搞不熟,后边就晕头转向了,在此重新归纳一下廖大神的函数教程,加深记忆 一.函数的参数分为: 位置参数 def power(x): # x 就是power(x)的一个位置参数,我们调用power(x ...

  8. Python学习笔记(四)Python函数的参数

    Python的函数除了正常使用的必选参数外,还可以使用默认参数.可变参数和关键字参数. 默认参数 基本使用 默认参数就是可以给特定的参数设置一个默认值,调用函数时,有默认值得参数可以不进行赋值,如: ...

  9. 使用可变对象作为python函数默认参数引发的问题

    写python的都知道,python函数或者方法可以使用默认参数,比如 1 def foo(arg=None): 2 print(arg) 3 4 foo() 5 6 foo("hello ...

  10. Python面试题目之Python函数默认参数陷阱

    请看如下一段程序: def extend_list(v, li=[]): li.append(v) return li list1 = extend_list(10) list2 = extend_l ...

随机推荐

  1. [Java][Liferay] 模拟用户

    以admin的帐号登陆 Navigation to Users and Organizations -> All Users 找到你要查看的user,点击Actions->Imperson ...

  2. cf1059D. Nature Reserve(三分)

    题意 题目链接 Sol 欲哭无泪啊qwq....昨晚一定是智息了qwq 说一个和标算不一样做法吧.. 显然\(x\)轴是可以三分的,半径是可以二分的. 恭喜你获得了一个TLE的做法.. 然后第二维的二 ...

  3. AngularJS 指令解析(二)

    AngularJS 指令解析(二) 第一篇我们讲过了作用域(scope)这块内容,现在我们进入正题,讲AngularJS的指令. 什么是指令? 这里我们引用官方的一句话: Custom directi ...

  4. iOS 谓词(NSPredicate)的应用

    Cocoa中谓词(Predicate)提供了一个通用的查询方式处理数据,可以获取和指定数据的过滤形式,Cocoa实际开发中可以是使用NSPredicate及其父类NSComparisonPredica ...

  5. Java项目性能瓶颈分析及定位(八)——Java线程堆栈分析(五)

    对于CPU而言,常见的瓶颈主要有两种:服务器的压力很小,但是CPU的利用率却很高,这样的性能瓶颈相对比较容易定位(好比我只是说了你一句,你就哭了,你的弱点立马就暴露出来了):给服务器施加的压力很大,但 ...

  6. 如何更换vim-airline的theme

    仓库位置: 点我直达 (主题以前是和airline在同个仓库的,现在独立出来了) 这些内置的这些主题,可以直接使用,方法是在 “.vimrc”文件中写 let g:airline_theme=&quo ...

  7. 洛谷 P1266 速度限制

    题目描述 在这个繁忙的社会中,我们往往不再去选择最短的道路,而是选择最快的路线.开车时每条道路的限速成为最关键的问题.不幸的是,有一些限速的标志丢失了,因此你无法得知应该开多快.一种可以辩解的解决方案 ...

  8. C#自定义规则对比两个集合的对象是否相等

    IList<获取的类> ret = 类的结果集; return ret.Except(另一个相同类型的对象列表集, new AClassComPare()): public class A ...

  9. 引用类型(二):Array类型

    一.js中的数组与其它语言中的数组的区别1.ECMAScript数组的每一项可以保存任何类型的数据2.ECMAScript数组的大小是可以动态调整的 二.创建数组的基本方式1.使用Array构造函数 ...

  10. 今天 小小收获, 看了 sam Xiao 的好帖子 明白了 泛型委托 的 意思。

    Func<int,int,int> cAdd1 = (int x, int y) => { return x + y; }; int result= aAdd1(1,2); cons ...