python 的学习已经进入到第四天,前面几章我们已经学会了基本的变量操作,以及分支结构和循环结构,那么本章,我们来说说 python 中的函数

1. 函数介绍

在开发程序中,如果需要调用某段代码多次,但是为了 提高编写的效率以及代码的可重用性,所以把具有独立功能的代码块 组织成一个独立的小模块,这就是函数。

在Python 中可以使用 def 关键字来定义函数,和变量一样每个函数也需要声明一个符合命名规范的名称。在函数后面的圆括号内可以放置我们需要传递的参数,待结果执行完毕我们也可以根据需要 使用 return 关键字返回调用结果。

 

案例:

我们先看一道数学题

事实上,上面的问题等同于将8个苹果分成四组每组至少一个苹果有多少种方案。想到这一点问题的答案就呼之欲出了。

如果我们还没有学过函数,我们可以这么写

"""
输入M和N 计算C(M,N)
version:0.1
author:coke
"""
m = int(input('m='))
n = int(input('n='))
fm = 1
for x in range(1,m + 1):
fm *= x
fn = 1
for y in range(1,n + 1):
fn *= y
fmn = 1
for z in range(1,m - n + 1):
fmn *= z
print(fm // fn // fmn)

 

你应该发现了,相似的for循环我们写了三遍,我们是不是可以做一个提取呢?

"""
用函数求分配方案
version: 0.1
author: coke
"""
#-*- coding:utf-8 -*-
def factorial(num):
"""
求阶乘
:param num 非负整数
:return num的阶乘
"""
result = 1
for n in range(1, num + 1):
result *= n
return result m = int(input("请输入一个数字m:"))
n = int(input("请输入一个数字n:"))
print(factorial(m)//factorial(n)//factorial(m-n))

 

2. 函数的参数

函数是绝大多数编程语言中都支持的一个代码的“构建块”,但是Python中的函数与其他语言中的函数还是有很多不太相同的地方,其中一个显著的区别就是Python对函数参数的处理。在Python中,函数的参数可以有默认值,也支持使用可变参数,所以Python并不需要像其他语言一样支持函数的重载 。所以我们定义一个函数时,可以让它有很多不同的使用方式.

from random import randint
def roll_rice(n = 2):
"""
:param n:色子数
:return: n颗色子的点数和
"""
total = 0
for _ in range(n):
total += randint(1,6)
return total
def add(a ,b = 0 ,c=0):
return a + b + c print(roll_rice(1))
print(roll_rice(1))
print(roll_rice(2))
print(roll_rice(2))
# 传递参数时可以不按照设定的顺序进行传递
print(add(c=50, a=100, b=200))

我们给上面两个函数的参数都设定了默认值,这也就意味着如果在调用函数的时候如果没有传入对应参数的值时将使用该参数的默认值,所以在上面的代码中我们可以用各种不同的方式去调用add函数,这跟其他很多语言中函数重载的效果是一致的。

其实上面的add 函数还有更好的实现方法,因为我们可能会 对 0个或多个参数进行加法运算,而具体有几个参数完全可以由调用者决定

#-*-coding:utf-8-*-
# 在参数名前面的*表示args是一个可变参数
# 即在调用add函数时可以传入0个或多个参数
def add(*args):
total = 0
argsType = type(args)
print("args的类型为:%s"%argsType)
for val in args:
total += val
return total print(add())
print(add(1))
print(add(1,2))
print(add(1,2,3))

 

3. 模块与函数

对于任何一种编程语言来说,给变量、函数这样的标识符起名字都是一个让人头疼的问题,因为我们会遇到命名冲突这种尴尬的情况。最简单的场景就是在同一个.py文件中定义了两个同名函数,由于Python没有函数重载的概念,那么后面的定义会覆盖之前的定义,也就意味着两个函数同名函数实际上只有一个是存在的。

"""
测试代码
version:0.1
author:coke
"""
def foo():
print("hello-world") def foo():
print("world-hello")
#下面的代码会输出什么? 是不是有点混乱
foo()

 

当然上面的这种情况我们很容易就能避免,但是如果项目是由多人协作进行团队开发的时候,团队中可能有多个程序员都定义了名为foo的函数,那么怎么解决这种命名冲突呢?答案其实很简单,Python中每个文件就代表了一个模块(module),我们在不同的模块中可以有同名的函数,在使用函数的时候我们通过import关键字导入指定的模块就可以区分到底要使用的是哪个模块中的foo函数,代码如下所示

module1.py

def foo():
print("hello-world")

module2.py

def foo():
print("world-hello")

moduleTest1.py

import module1 as m1
import module2 as m2
#输出 hello-world
m1.foo()
#输出 world-hello
m2.foo()

 

但是如果将代码写成了下面的样子,那么程序中调用的是最后导入的那个foo,因为后导入的foo覆盖了之前导入的foo

moduleTest2.py

from module1 import foo
from module2 import foo # 输出goodbye, world!
foo()

 

需要说明的是,如果我们导入的模块除了定义函数之外还中有可以执行代码,那么Python解释器在导入这个模块时就会执行这些代码,事实上我们可能并不希望如此,因此如果我们在模块中编写了执行代码,最好是将这些执行代码放入如下所示的条件中,这样的话除非直接运行该模块,if条件下的这些代码是不会执行的,因为只有直接执行的模块的名字才是'__main__'

def foo():
pass
def bar():
pass # _name_ 是Python中一个隐含的变量它代表了模块的名字
# 只有被python解释器直接执行的模块的名字是 __main__
if __name__ == '__main__':
print('call foo')
foo()
print("call bar")
bar

 

4. 递归函数

递归函数:如果一个函数在内部不调用其它的函数,而是自己本身的话,这个函数就是递归函数。

 

举个例子:我们来计算阶乘 n! = 1 * 2 * 3 * ... * n

方案1:循环解决

"""
while 循环算阶乘
version:0.1
author:coke
"""
# -*- coding:utf-8 -*-
def calNum(num):
i = 1
result = 1
while i <= num:
result *= i
i += 1
return result total = calNum(4)
print(total)

 

方案2:递归函数

"""
while 循环算阶乘
version:0.1
author:coke
"""
# -*- coding:utf-8 -*-
def calNum(num):
if num > 1:
result = num * calNum(num - 1)
else:
result = 1
return result total = calNum(4)
print(total)

 

5. 匿名函数

lambda关键词能创建小型匿名函数。这种函数得名于省略了用def声明函数的标准步骤。

lambda函数的语法只包含一个语句,如下:

   lambda [arg1 [,arg2,.....argn]]:expression

 

1. 使用匿名函数求两数之和(自己定义函数 )

"""
匿名函数测试
version:0.1
author:coke
"""
def add(a,b):
return a+b result1 = add(1,6)
# 使用lambda 表达式
sum = lambda x,y: x+y
result2 = sum(1,6)
print(result1)
print(result2)

 

2. 数据排序 (作为内置函数的参数 )

"""
匿名函数作为内置函数进行排序
关于 字典和列表的知识点后面会讲
version:0.1
author:coke
"""
stus = [
{"name":"zhangsan", "age":18},
{"name":"lisi", "age":19},
{"name":"wangwu", "age":17}
]
stus.sort(key = lambda x:x['name'])
print(stus)

 

6. 多返回值

在python中 一个函数可不可以返回多个 返回值呢?

"""
多返回值的测试
version:0.1
author:coke
"""
def cal(a,b):
add = a+b
mul = a*b
return add,mul result = cal(2,3)
print(result)

输出结果

 

一个函数,返回多个返回值 ,本质上是利用了元组的特性。

注:关于元组,列表,字典的知识点后面会讲,这里先提一嘴。

Python集训营45天—Day04 (函数)的更多相关文章

  1. Python集训营45天—Day01

    目录 1. Python简介 2. 第一个Python程序 3. 知识点梳理 序言:未来是数据的世界,而python 是一门可以高效简洁处理数据的语言,博主打算花45天左右完成python学习的从0到 ...

  2. Python集训营45天—Day02

    目录 变量和运算符 1.1 初步介绍 1.2 使用案例 1.3 知识点梳理 1.4 练习 序言:这一章我们将学习变量以及常见的类型,我们将以案例和代码相结合的方式进行梳理,但是其中所有的案例和知识点 ...

  3. Python集训营45天—Day03

    目录 1. 分支结构 1.1 初步介绍 1.2 使用案例 1.3 练习 2.循环结构 1.1 初步介绍 1.2 使用案例 1. 分支结构 1.1 初步介绍 至今,我们所写的Python代码都是顺序执行 ...

  4. Python集训营45天—Day08 (文件操作)

    目录 1. 文件操作介绍 2. 文件的读写 2.1 文本文件 2.2 二进制文件 2.3 JSON文件 3. 文件的定位,重命名和删除 4. 文件夹的相关操作 1. 文件操作介绍 大家应该听说过一句话 ...

  5. Python集训营45天—Day07 (面向对象编程进阶)

    目录 1. @property装饰器 2. 魔法方法 3. 类属性和实例属性 4.静态方法和类方法 5. 单继承和多继承 6. 多态 7. del 方法 序言:上个章节我们了解了面向对象的基础知识,这 ...

  6. 2020牛客寒假算法基础集训营2 J.求函数 (线段树 推公式 单点修改 区间查询)

    https://ac.nowcoder.com/acm/contest/3003/J 题解: #include<bits/stdc++.h> typedef long long ll; u ...

  7. 8.10 正睿暑期集训营 Day7

    目录 2018.8.10 正睿暑期集训营 Day7 总结 A 花园(思路) B 归来(Tarjan 拓扑) C 机场(凸函数 点分治) 考试代码 A B C 2018.8.10 正睿暑期集训营 Day ...

  8. 8.5 正睿暑期集训营 Day2

    目录 2018.8.5 正睿暑期集训营 Day2 总结 A.占领地区(前缀和) B.配对(组合) C 导数卷积(NTT) 考试代码 T1 T2 T3 2018.8.5 正睿暑期集训营 Day2 时间: ...

  9. 8.4 正睿暑期集训营 Day1

    目录 2018.8.4 正睿暑期集训营 Day1 A 数对子 B 逆序对 C 盖房子 考试代码 A B C 2018.8.4 正睿暑期集训营 Day1 时间:4.5h(实际) 期望得分:30+50+3 ...

随机推荐

  1. 【java提高】(18)---静态内部类和非静态内部类

    java提高](18)-静态内部类和非静态内部类 定义 放在一个类的内部的类我们就叫内部类. 自己从开发到现在其实用到内部类主要在两个地方会考虑用内部类: 1.使用静态内部类的单例模式 2.将Json ...

  2. Windows Server 2008配置系统安全策略

    下面学习Windows Server 2008配置系统安全策略 在工作组中的计算机本地安全策略有 用户策略,密码策略,密码过期默认42天 服务账户设置成永不过期,帐户锁定策略,本地策略,审核策略,计算 ...

  3. npm钉钉脚手架,支持考勤信息获取

    钉钉官方并未提供nodejs包,第一次调用接口的时候非常费事,而且尝试去寻找相关的钉钉考勤数据模块的时候只找到了一些消息啊,只能办公啊,免登啊之类的模块,有关考勤数据的似乎没有 关于dd的npm包中一 ...

  4. 版本管理·玩转git(快速入门git)

    如果你用过Word文档写过文章,那么你一定会有这样的经历. 我觉得某一段或者某一句写得不够好,但是,删掉之后我可能会后悔把它删掉了,进而又想把删掉的段落找回来,这时,你想到了一个好办法,将每次的修改都 ...

  5. PythonI/O进阶学习笔记_2.魔法函数

    前言: 本文一切观点和测试代码是在python3的基础上. Content: 1.什么是魔法函数,魔法函数__getitem__在python中应用. 2.python的数据模型和数据模型这种设计对p ...

  6. 使用css实现水平垂直居中

    1.通过absolute和margin实现(适用于弹窗,具体位置随浏览器屏幕大小变化改变)这种方式需要居中元素的父级必须采用绝对定位或相对定位,被居中元素的尺寸需要固定. <div class= ...

  7. zookeeper学习之原理

    一.zookeeper 是什么 Zookeeper是一个分布式协调服务,可用于服务发现,分布式锁,分布式领导选举,配置管理等.这一切的基础,都是Zookeeper提供了一个类似于Linux文件系统的树 ...

  8. JIRA使用过程出现问题整理解答

    转自:http://www.51testing.com/html/44/n-2820444.html 发表于:2015-5-28 10:22  作者:知乎   来源:51Testing软件测试网采编 ...

  9. HDU 2561 二小整数

    第二小整数 Time Limit: 3000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total Subm ...

  10. HTML5基本介绍

    HTML5简介 HTML是互联网上应用最广泛的标记语言.HTML文件就是普通文本+HTML标记,而不同的HTML标记能表示不同的效果.(简单的说HTML是超文本标记语言) HTML5草案的前身名为 W ...