王亟亟的Python学习之路(六)-递归,迭代,列表生成式

转载请注明出处:王亟亟的大牛之路

最近事情比较多,也没什么时间学习。(借口,明明在偷懒)
难得空下来,就继续把文章写下去。(玩手游时间更多)

在贴今天要写的内容之前还是先说一下某些概念!(概念还是很重要的,虽然更重要的是理解)

什么是递归?(维基来的)

白话的理解就是某函数自己调用自己

大牛的分析:

递归的基本思想是把规模大的问题转化为规模小的相似的子问题来解决。在函数实现时,因为解决大问题的方法和解决小问题的方法往往是同一个方法,所以就产生了函数调用它自身的情况。另外这个解决问题的函数必须有明显的结束条件,这样就不会产生无限递归的情况了。

什么是迭代?

迭代是函数内某段代码实现循环

迭代和普通循环的区别?

循环代码中参与运算的变量同时是保存结果的变量,当前保存的结果作为下一次循环计算的初始值。
递归循环中,遇到满足终止条件的情况时逐层返回来结束。

平时场景可能是这样子的:

表生成式是Python中对上述两种模式的封装,之后会详细给大家说明


今天的大部分例子将会用Java和Python来实现两种相同效果下的不同代码,让他加会觉得高级语言是有多么方便编写(不是黑Java 毕竟是老牌语言啊 哈哈)

递归的概念在上面已经简单的描述了,这下就简单的写个例子:

如何实现1*2*3*4*5?

最2B的写法:

def aa(a,b,c,d,e):
    return a*b*c*d*e
print(aa(1,2,3,4,5))

结果:120

那如果是20个,30个参数呢?难道我再传入20个,30个参数吗?
我们可以从业务逻辑中找前后数字的逻辑关系

x,x+1,x+1+1…依次递增

那我们就可以写一个方法如下:

def aa(flag):
    if flag==1:
        return 1
    return flag*aa(flag-1)

结果也是上面的120

java中:

  public static void main(String[] asa) {
        System.out.println(mRecursive(5,1));
    }

    public static int mRecursive(int flag,int value) {
        if (flag == 1)
                return value;
        return mRecursive(flag-1,value*flag);
    }

结果也是120

但是过度的调用会使得栈溢出,所以引入尾递归,在函数返回的时候,调用自身本身,并且,return语句不能包含表达式。而是返回一个已经存在的值,这样就避免了栈溢出,因为永远只有一个栈

代码如下:

#尾递归方式
def fact_iter(num, k):
    if num == 1:
        return k
    return fact_iter(num - 1, num * k)

def fact(n):
    return fact_iter(n, 1)

调用fact(5)结果也是 120

是不是很方便?当然刚开始的时候会对这一类的概念会很混乱(跪拜算法大牛啊)

那要么尝试算下Fibonacci数列的前X位?
答案会在git中呈现


最常用的迭代就是用for,while之类的循环去遍历一个数组/元组等内的元素,如:

nList=[]
flagK=4
for i in range(flagK):
    nList.append(listA[i])
print("第38行打印",nList)

结果:第38行打印 [1, 3, 5, 7]

在Java中:

    public static void main(String[] asa) {
        ArrayList<Integer> list = new ArrayList<Integer>();
        for (int k = 0; k < 10; k++) {
            list.add(k);
        }

        System.out.println(list);
    }

    结果:[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]

还可以迭代字符串,dic等

d={"a":1,"b":2,"1b":3}
for value1 in d:
    print(value1,end=" ")
print("第66行,迭代一个字典的key,但是是无序的哦")

结果   a 1b b 第66行,迭代一个字典的key,但是是无序的哦

for value2 in d.items():
    print(value2,end=" ")
print("第70行,迭代一个字典,但是是无序的哦")

结果   ('a', 1) ('1b', 3) ('b', 2) 第70行,迭代一个字典,但是是无序的哦

//需要导包
from collections import Iterable
print("第74行判断对象是否能被迭代",isinstance('abc', Iterable))

结果   第74行判断对象是否能被迭代 True

print("第75行判断对象是否能被迭代",isinstance(False, Iterable))

结果   第75行判断对象是否能被迭代 False

//迭代list并显示下标
for i, value in enumerate(['A', 'B', 'C']):
     print(i, value,end="   ")
print("第78行,显示下标需要调用enumerate函数")

结果   0 A   1 B   2 C   第78行,显示下标需要调用enumerate函数

//多项迭代
for x, y,z in [(1, 1, 3), (3,2, 4), (4,3, 9)]:
    print(x, y,z,end="     ")

结果:   1 1 3     3 2 4     4 3 9

而在Python中,提供了更简便的功能“切片”,切片有什么效果?

listA原型: [1, 3, 5, 7, 9, 11, 13, 15, 17, 19, 21, 23, 25, 27, 29, 31, 33, 35, 37, 39, 41, 43, 45, 47, 49, 51, 53, 55, 57, 59, 61, 63, 65, 67, 69, 71, 73, 75, 77, 79, 81, 83, 85, 87, 89, 91, 93, 95, 97, 99]

print("第41行切片操作",listA[0:3])

结果  第41行切片操作 [1, 3, 5]

print("第42行切片操作,取最后一个",listA[-1])
结果   第42行切片操作,取最后一个 99
//Python支持L[-1]取倒数第一个元素

print("第43行切片操作,取倒数三个,左边元素不包括自己",listA[-4:-1])
结果   第43行切片操作,取倒数三个,左边元素不包括自己 [93, 95, 97]
//诸如 L[0:3]表示,从索引0开始取,直到索引3为止,但不包括索引3。即索引0,1,2,正好是3个元素。

print("第44行,用切片创建10位的list",list(range(10)))
结果   第44行,用切片创建10位的list [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
//可以通过切片轻松取出某一段数列

print("第45行,前10个数,每两个取一个",listA[:10:2])
结果  第45行,前10个数,每两个取一个 [1, 5, 9, 13, 17]

print("第46行每两个取一个",listA[::2])
结果  第46行每两个取一个 [1, 5, 9, 13, 17, 21, 25, 29, 33, 37, 41, 45, 49, 53, 57, 61, 65, 69, 73, 77, 81, 85, 89, 93, 97]

print("第47行复制原来的集合",listA[:])
结果 第47行复制原来的集合 [1, 3, 5, 7, 9, 11, 13, 15, 17, 19, 21, 23, 25, 27, 29, 31, 33, 35, 37, 39, 41, 43, 45, 47, 49, 51, 53, 55, 57, 59, 61, 63, 65, 67, 69, 71, 73, 75, 77, 79, 81, 83, 85, 87, 89, 91, 93, 95, 97, 99]
//只写[:]就可以原样复制一个list

还可以对字符串,元组等进行切片

mTuple=(1,2,3,4,5,6,7,8,9,10)
print('第51行,元组切片',mTuple[2:10])
结果   第51行,元组切片 (3, 4, 5, 6, 7, 8, 9, 10)

print("第52行,元组复制",mTuple[::])

结果   第52行,元组复制 (1, 2, 3, 4, 5, 6, 7, 8, 9, 10)

#对字符串进行切片
##字符串的切片
print('第55行,切片HelloWorld,返回的也是字符串','helloworld'[2:6])
结果:   第55行,切片HelloWorld,返回的也是字符串 llow

列表生成式

Python内置的非常简单却强大的可以用来创建list的生成式

例子:
如果要列出0-20内%==0的数呢?

Java:

  for (int k = 0; k < 20; k++) {
         if (k % 3 == 0) {
              list1.add(k);
          }
   }
  System.out.println(list1);

结果:   [0, 3, 6, 9, 12, 15, 18]

Python循环:

La=[]
for x in range(20):
    if x%3==0:
      La.append(x)
print(La)

结果:   [0, 3, 6, 9, 12, 15, 18]

那如果使用列表生成式呢?

print("第86行列表生成表达式",[x for x in range(20) if x%3==0])

结果:   第86行列表生成表达式 [0, 3, 6, 9, 12, 15, 18]
//是不是代码量少了许多,而且可读性也很强

//其他演示

print("第87行,多层循环",[m + n for m in 'ABCD' for n in 'XYZ'])
结果:   第87行,多层循环 ['AX', 'AY', 'AZ', 'BX', 'BY', 'BZ', 'CX', 'CY', 'CZ', 'DX', 'DY', 'DZ']

print("第89行循环读出同级目录内容",[d for d in os.listdir('.')])
结果:   第89行循环读出同级目录内容 ['.idea', 'l2demo.py', 'l3demo.py', 'l4demo.py']

这3个功能模块在我们平时的代码编写中的出现几率很高,而Python的大牛们已经给我们写好现成的了,我们只需要使用即可

源码地址:https://github.com/ddwhan0123/PythonExample/blob/master/%E7%A4%BA%E4%BE%8B/l4demo.py

感谢点个赞!

时间: 2024-08-02 18:50:39

王亟亟的Python学习之路(六)-递归,迭代,列表生成式的相关文章

王亟亟的Python学习之路(四)-循环,条件,Range,list和tuple

转载请注明出处:王亟亟的大牛之路 这是本次Python学习历程的第4篇,之前的文章:传送门 这篇主要讲以下几个知识点 - 循环 - 条件语句 - range函数 - list - tuple 循环 Python中的循环语句有 for 和 while.同样需要注意冒号和缩进.另外,在Python中没有do..while循环. 需要注意冒号和缩进,因为没有{}来帮助我们把循环里面的内容封起来 while循环 while 判断逻辑: 业务内容 或者for-in循环 names = ['12',12,

王亟亟的Python学习之路(五)-dictionary,set,函数,函数参数

转载请注明出处王亟亟的大牛之路 上一篇说的是循环,条件,Range,list和tuple,今天将从函数(方法)开始进一步的学习 -dictionary -set -函数 -函数参数 dictionary 键-值(key-value)存储,具有极快的查找速度.为什么反复提起查询速度,因为如果你一个用list只是为了获取里面X元素内容的话性能是相对比较查的,极力推荐"字典",字典也在第三片文章中有列出,但是这里还是再丰富下他的一些常用方法. 如何获检索dic内的值 dic={'wjj':1

王亟亟的Python学习之路(一)-环境搭建

轉載請注明出處王亟亟的大牛之路 楼主因为正好对Python这门高级语言感兴趣,然后经过一定的学习,总结下一些经验和知识点,分享给大家,这一系列会由浅至深,因为本身就不是从业余Python相关开发纯粹兴趣,如有不对请提出,谢谢哈! 言归正传,这篇讲下简单的环境搭建,百度其实也有,但是还要自己找资源,楼主在这边给各位客官都整理好了,您只需要下载一下就好了,哈哈 现在主流的有Python2.x系列和3.x系列.我的一系列文章将从3.X的版本展开,请大家理解,这其中还是会有很大区别的! 首先 贴下载地址

王亟亟的Python学习之路(10)-匿名函数

转载请注明出处:王亟亟的大牛之路 又有好多天没有碰Python的东西了,下午抽出点时间就补一篇介绍匿名函数 匿名函数在很多语言里都有,它可以使代码更加简洁.紧凑,模块化程度更高. 在jdk8里发现了lambda表达式的影子 以前我们要循环一个集合需要这样 List<Integer> numbers = Arrays.asList(1, 2, 3, 4, 5, 6); for (int number : numbers) { System.out.println(number); } 现在可以这

王亟亟的Python学习之路(九)-sorted()排序以及简单字符串处理

转载请注明出处:王亟亟的大牛之路 这一片就讲2个知识点,1排序,2字符串处理 Python在排序操作的这一部分做了很好的封装,我们不需要写太多代码就可以实现排序的效果,先贴下Java的实现.(这里不是黑Java!!!!) public class 直接插入排序 { public static void main(String[] args) { int[] a={49,38,65,97,76,13,27,49,78,34,12,64,1}; System.out.println("排序之前:&q

王亟亟的Python学习之路(二)-项目创建以及要点提及

转载请注明出处王亟亟的大牛之路 首先,说一下上一篇为什么虽说我们是从3.X开始说起,那就要说明下2个版本的区别(上下版本几乎没关系) Python的3​​.0版本,常被称为Python 3000,或简称Py3k.相对于Python的早期版本,这是一个较大的升级. 为了不带入过多的累赘,Python 3.0在设计的时候没有考虑向下相容.不兼容哦!! 许多针对早期Python版本设计的程式都无法在Python 3.0上正常执行. 为了照顾现有程式,Python 2.6作为一个过渡版本,基本使用了Py

王亟亟的Python学习之路(三)-基础语法以及基本数据类型

转载请注明出处:王亟亟的大牛之路 理论知识虽然很枯燥,但是你以后的高度取决于你基础的厚度 每种语言多多少少都有它的保留关键字 JAVA的: Python的: 那关键字是什么? 电脑语言里事先定义的,有特别意义的标识符,有时又叫保留字,还有特别意义的变量. 注释 java: -单行 // -多行/** **/ Python: 单行# 多行''' 数据类型 整数:诸如 1 2 3 -1 -2 10 0 这种都算,当然计算机是 2进制干活的,所以 2进制 10进制 16进制的整形数据都算....你懂的

王亟亟的Python学习之路(八)-函数式编程,map(),reduce(),filter()

转载请注明出处:王亟亟的大牛之路 首先在这里祝愿大家,新年快乐,工作顺利,BUG少少!!! 本来说是在春节假期内继续维持着写文章的进度,但是还是偷懒了几天(打了4天SC2哈哈哈) 今天上的是关于Python的文章,毕竟在亲戚家拜年,懒得插各类手机调试什么的,况且确实好久没有弄Python了,就写了,废话不多,开始正题!! 函数式编程 函数是什么? 把复杂的操作化为简单的函数分解成简单的操作,这种操作就是面向过程,也就是C这类的实现的大体概念. 函数式是什么? 函数没有变量,任意一个函数,只要输入

王亟亟的Python学习之路(10)-函数对象的作用域,函数作为返回值,闭包

转载请注明出处:王亟亟的大牛之路 本来打算把工作的事周末做掉点,但是发现在外面浪并不能迅速集中投入,为了避免不必要的BUG 还是明天在家做吧,那么久写一篇Python的文章吧,毕竟背着Mac出门不做些太对不起自己的肩膀了 废话不多,直接说内容,这篇文章的内容大致是围绕"闭包"走的,介绍下相关理论知识 作用域:对象有其存活的范围 闭包:内部函数可以引用外部函数的参数和局部变量(是不是听得云里雾里的,没事 看例子就明白了) 就像循环内声明的对象,除了循环也就无法获取他的值一样.就像在jav