杨辉三角定义如下:

          1
/ \
1 1
/ \ / \
1 2 1
/ \ / \ / \
1 3 3 1
/ \ / \ / \ / \
1 4 6 4 1
/ \ / \ / \ / \ / \
1 5 10 10 5 1

把每一行看做一个list,试写一个generator,不断输出下一行的list。

该题目考查生成器的应用。一般的思路是,首先在每一行输出一个1,随后通过循环,位置i(从2开始)的数是上一行i与i-1位置的数之和,当i与上一行数字个数相同时,循环终止,最后再添加进一个1,形成新的一行。

基于这个基本思路,将python的生成器运用到里面,有两种常见的写法:

一种写法如下:

 def triangles():#杨辉三角的一种生成方法
l = [1]
while True :
yield l
for i in range ( 1,len (l) ) :
l [i] = h [i] + h [i-1]
l.append (1)
h = l[:]

另外一种写法如下,运用了list的生成式:

 def triangles():
l = [1]
while True :
yield l
l = [1] + [ l[i] + l[i+1] for i in range ( len (l) - 1)] + [1]

可以看到,以上两种写法都是相当简洁的。一开始这两个代码看不太懂,比如说为啥第一种写法里一开始h里面没有数,却也能够正常执行?主要是对于生成器的yield机制不明白,以及对于range的用法不是特别清楚。以下就这两点分别解释。

首先,当函数中出现了yield之后,该函数就不再被视为函数,而视为一个生成器。此时,整个函数被使用的语句流程会发生改变,一般的函数都是调用的时候从函数入口进,发现return或函数执行完毕后返回,而生成器函数则是每次调用函数执行,执行到yield返回,下次再调用函数的时候从上次yield返回处继续执行。

其次,range的用法中是,如果是【range(x,x) 其中x是常量】的形式,range依然返回空。故在上述代码的for循环中,由于在第一次试图循环的时候,后面的range要么是range(1,1)要么是range(0),故都会成功避开i或者h没有实际值的循环,执行接下来的部分。当第二次试图循环开始时,i和h内的内容都已经满足条件了,所以就能正常运行了。

还有一种我看到的最简单的写法:

 def triangles():
L = [1]
while True:
yield L
L= [(L + [0])[i] + ([0] + L)[i] for i in range(len(L)+1)]

这一种写法直接去掉了第二种写法里每次L两边额外插入的[1],使其变为了一个完整的一个list生成式,可以说是相当精妙。

那么,这种写法为什么也可以呢?我们再来分析一下杨辉三角的性质,这样,为了直观理解,我们先利用上面的代码,举一个运行中的过程例子。

比如,L此时为[1,1](杨辉三角第二行),现在需要求第三行。根据第五行的生成式,将按照以下步骤进行计算:

1.L尾部加0,得到[1,1,0],我们称之为tempL1

2.L首部加0,得到[0,1,1],我们称之为tempL2

3.现在,根据之后的for循环,L最终要被赋值成由tempL1与tempL2对应的每个相同位置数字之和所组成的列表,经过计算,这个新的L应该为[1,2,1]。居然确实是杨辉三角的第三行!

相信聪明的观众已经明白了,这个最简单的写法是利用了杨辉三角本身的对称性质,让同一行错开一位竖式相加,得到的就是下一行的结果。同时,利用python里面本身就极为方便的列表扩展写法和列表生成式,才有了第三种如此简洁的写法~

【Python初级】由生成杨辉三角代码所思考的一些问题的更多相关文章

  1. python 生成器生成杨辉三角

    用Python写趣味程序感觉屌屌的,停不下来 #生成器生成展示杨辉三角 #原理是在一个2维数组里展示杨辉三角,空的地方用0,输出时,转化为' ' def yang(line): n,leng=0,2* ...

  2. 经典问题(c++/python)素数、杨辉三角(金字塔型)、统计单词数、简单计算器、密码安全程度、凯撒密码加密、汉诺塔 (python课设实验实例)-- biaobiao88

    [编写程序,输人一个大于2的自然数,然后输出小于该数字的所有素数组成的列表.]所谓素数,是指除了1和自身之外没有其他因数的自然数,最小的素数是2,后面依次是3.5.7.11.13... c++代码: ...

  3. 给定一个非负整数 numRows,生成杨辉三角的前 numRows 行。

    该题还是考杨辉三角计算,只不过最后每一行都放入List集合中,然后返回,直接看代码: public static List<List<Integer>> generate(in ...

  4. Python使用函数实现杨辉三角

    运行效果: 可在函数中指定阶层数,输出对应的杨辉三角 源代码如下: 1 # -*-coding:utf-8 -*- 2 ''' 3 chapter4_do.py 4 函数yanghui(n)用于输出n ...

  5. python-generator生成杨辉三角

    根据廖雪峰老师的评论区摘录. 1: def triangles(): L = [1] while True: yield L L1 = [0] + L[:] L = [L[i]+L1[i] for i ...

  6. Python实现杨辉三角,超详细!

    巧妙实现杨辉三角代码 def triangles(): N=[1] #初始化为[1],杨辉三角的每一行为一个list while True: yield N #yield 实现记录功能,没有下一个ne ...

  7. LeetCode118 杨辉三角 Python

    给定一个非负整数 numRows,生成杨辉三角的前 numRows 行. 示例:输入: 5 输出: [ [1], [1,1], [1,2,1], [1,3,3,1], [1,4,6,4,1] ] cl ...

  8. python输出杨辉三角

    使用python列表,展示杨辉三角 # !/usr/bin/env python # -*- coding:utf-8 -*- # Author:Hiuhung Wan yanghui = [] fo ...

  9. leetcode 118. 杨辉三角(python)

    给定一个非负整数 numRows,生成杨辉三角的前 numRows 行. 在杨辉三角中,每个数是它左上方和右上方的数的和. 示例: 输入: 5输出:[ [1], [1,1], [1,2,1], [1, ...

随机推荐

  1. poi对word的操作(总结)

    ★★★ POI在读写word docx文件时是通过xwpf模块来进行的,其核心是XWPFDocument.    1.正文段落:一个文档包含多个段落Paragraph,一个段落包含多个Runs,一个R ...

  2. 782E. Underground Lab DFS 好题

    Link 题意:给出一个图,有n个点,m条边,k个人,每个人至多只能走$\lceil\frac{2n}{k}\rceil$步,输出可行的方案即输出每个人所走的步数和所走点 思路: 由于保证给出的是连通 ...

  3. Lua的各种资源1

    Libraries And Bindings     LuaDirectory > LuaAddons > LibrariesAndBindings This is a list of l ...

  4. 2017ACM暑期多校联合训练 - Team 2 1011 HDU 6055 Regular polygon (数学规律)

    题目链接 **Problem Description On a two-dimensional plane, give you n integer points. Your task is to fi ...

  5. Python自定义web框架、Jinja2

    WSGI(Web Server Gateway Interface)是一种规范,它定义了使用python编写的web app与web server之间接口格式,实现web app与web server ...

  6. 带你优雅的使用 icon

    前言 本篇文章其实陆陆续续写了快半年,主体部分写好了很久了,但由于种种原因一直没有发布.首先来说说写这篇文章的主要初衷是:在做前端后台项目的时候经常会用到很多 icon 图标,刚开始还好,但随着项目的 ...

  7. 生成验证码tp

    js里拼接随机数 页面上链接 去掉后缀名

  8. 自己看之区间DP

    //菜鸡制作,看的时候可能三目运算符略烦;;; 区间DP入门题:Brackets 地址:http://59.77.139.92/Problem.jsp?pid=1463 分析(对区间DP的代码原理进行 ...

  9. tomcat和weblogic的区别

    Tomcat是Apache基金会提供的Servlet容器,它支持JSP, Servlet和JDBC等J2EE关键技术,所以用户可以用Tomcat开发基于数据库,Servlet和JSP页面的Web应用, ...

  10. 选择问题(选择数组中第K小的数)

    由排序问题可以引申出选择问题,选择问题就是选择并返回数组中第k小的数,如果把数组全部排好序,在返回第k小的数,也能正确返回,但是这无疑做了很多无用功,由上篇博客中提到的快速排序,稍稍修改下就可以以较小 ...