Python学习记录2

  • map函数,批量计算数据


    Python学习记录2_第1张图片
    Paste_Image.png
list(map(str, [1, 2, 3, 4, 5, 6, 7, 8, 9]))
['1', '2', '3', '4', '5', '6', '7', '8', '9']

Python中转变大小写的直接函数有以下方法:
upper()——所有字母大写
lower()——所有字母小写
capitalize()——首字母大写,其他字母小写
title()——所有单词首字母大写,其他小写

def normalize(name):
    return str.capitalize(name)

L1 = ['adam', 'LISA', 'barT']
L2 = list(map(normalize, L1))
print(L2)
  • reduce函数,计算结果不断迭代

  • filter 过滤函数

注意到filter()函数返回的是一个Iterator,也就是一个惰性序列,所以要强迫filter()完成计算结果,需要用list()函数获得所有结果并返回list。

def NumIsOdd(Num):
    return Num%2==1
# list后面的括号是类型转化用的
print(list(filter(NumIsOdd,[1,2,3,4,5])))
  • 打印素数

计算素数的一个方法是埃氏筛法,它的算法理解起来非常简单:
首先,列出从2开始的所有自然数,构造一个序列:
2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, ...取序列的第一个数2,它一定是素数,然后用2把序列的2
的倍数筛掉:3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, ...
取新序列的第一个数3,它一定是素数,然后用3把序列的3的倍数筛掉:5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, ...取新序列的第一个数5,然后用5把序列的5的倍数筛掉:7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, ...不断筛下去,就可以得到所有的素数。

# 生成器
def _odd_iter():
    n=1
    while True:
        n = n + 2
        yield n

# 刷选函数
def _not_divisible(n):
    return lambda x : x % n > 0

# 定义一个生成器,不断地返回下一个素数
def primes():
    yield 2
    it = _odd_iter()  # 初始化奇数序列
    while True:
        n = next(it)
        yield n
        it = filter(_not_divisible(n),it)   # 构造新序列


# 打印1000以内的素数:
for n in primes():
    if n < 1000:
        print(n)
    else:
        break
  • 回数是指从左向右读和从右向左读都是一样的数,例如12321,909。请利用filter()滤掉非回数:
def is_palindrome(n):
    return str(n)==str(n)[::-1]

output = filter(is_palindrome, range(1, 1000))
print(list(output))
  • 为什么以下可以删除空字符?
    strip函数会去掉字符串头尾指定的字符,默认为空格,返回的是生成的新字符串;若下面的字符中是空字符,那么去掉后就是空了,and之后就为False。
def not_empty(s):
    return s and s.strip()

list(filter(not_empty, ['A', '', 'B', None, 'C', '  ']))
# 结果: ['A', 'B', 'C']
  • sorted函数
    假设我们用一组tuple表示学生名字和成绩,对齐用成绩进行排序
def by_name(t):
    return t[1]

L = [('Bob', 75), ('Adam', 92), ('Bart', 66), ('Lisa', 88)]
L2 = sorted(L, key=by_name)
print(L2)
  • 函数返回一个函数的时候,每次都会返回一个新的函数

  • 装饰器解释
    Python装饰器为什么难理解?
    理解 Python 装饰器看这一篇就够了
    [Python]写个带参数的装饰器

def log(func):
    def wrapper(*args, **kw):
        print('call %s():' % func.__name__)
        return func(*args, **kw)
    return wrapper

@log
def now():
    print('2015-3-25')

返回

>>> now()
call now():
2015-3-25

调用now的时候,实际上是调用log,然后以now作为参数。
调用log后,看到只定义了并返回了函数wrapper,就调用了wrapper,wrapper第一句打印函数的名字,还是now,接下来,wrapper返回func的调用,也就是now真正执行了。

如果decorator本身需要传入参数,那就需要编写一个返回decorator的高阶函数,写出来会更复杂。比如,要自定义log的文本:

def log(text):
    def decorator(func):
        def wrapper(*args, **kw):
            print('%s %s():' % (text, func.__name__))
            return func(*args, **kw)
        return wrapper
    return decorator

这个3层嵌套的decorator用法如下:

@log('execute')
def now():
    print('2015-3-25')

执行结果如下:

>>> now()
execute now():
2015-3-25

调用now的时候,实际上执行函数log,返回decorator的执行,返回wrapper的执行,wrapper执行就是结果了。

  • @property,将设置属性变得更加简单,这里实际上是一个修饰器,跟修饰器的代码比较下。

class Screen(object):

    @property
    def width(self):
        return self._width

    @width.setter
    def width(self, val):
        self._width = val

    @property
    def height(self):
        return self._height


# test:
s = Screen()
s.width = 1024
#can't allowed!!
#  s.height = 768

print(s.width, s.height)
  • Python内置的logging模块可以非常容易地记录错误信息:
# err_logging.py

import logging

def foo(s):
    return 10 / int(s)

def bar(s):
    return foo(s) * 2

def main():
    try:
        bar('0')
    except Exception as e:
        logging.exception(e)

main()
print('END')
  • if name == 'main':的作用是什么?
    运行第一个模块的时候,模块内建的变量name是‘main’,而其他次序运行的name就是模块的名字,因此这个判断直接的作用就是判断模块是不是首先被执行,或者是被首先执行的模块import的。

你可能感兴趣的:(Python学习记录2)