原文地址:http://python.jobbole.com/87380/

我们知道,迭代器的特点是:惰性求值(Lazy evaluation),即只有当迭代至某个值时,它才会被计算,这个特点使得迭代器特别适合于遍历大文件或无限集合等,因为我们不用一次性将它们存储在内存中。

Python 内置的 itertools 模块包含了一系列用来产生不同类型迭代器的函数或类,这些函数的返回都是一个迭代器,我们可以通过 for 循环来遍历取值,也可以使用 next() 来取值。

itertools 模块提供的迭代器函数有以下几种类型:

无限迭代器:生成一个无限序列,比如自然数序列 1, 2, 3, 4, ...;

有限迭代器:接收一个或多个序列(sequence)作为参数,进行组合、分组和过滤等;

组合生成器:序列的排列、组合,求序列的笛卡儿积等;

无限迭代器

itertools 模块提供了三个函数(事实上,它们是类)用于生成一个无限序列迭代器:

count(firstval=0, step=1)创建一个从 firstval (默认值为 0) 开始,以 step (默认值为 1) 为步长的的无限整数迭代器

cycle(iterable)对 iterable 中的元素反复执行循环,返回迭代器

repeat(object [,times]反复生成 object,如果给定 times,则重复次数为 times,否则为无限

下面,让我们看看一些例子。

count

count() 接收两个参数,第一个参数指定开始值,默认为 0,第二个参数指定步长,默认为 1:

>>> import itertools
>>>
>>> nums = itertools.count()
>>> for i in nums:
... if i > 6:
... break
... print i
...
0
1
2
3
4
5
6
>>> nums = itertools.count(10, 2) # 指定开始值和步长
>>> for i in nums:
... if i > 20:
... break
... print i
...
10
12
14
16
18
20

cycle

cycle() 用于对 iterable 中的元素反复执行循环:

>>> import itertools
>>>
>>> cycle_strings = itertools.cycle('ABC')
>>> i = 1
>>> for string in cycle_strings:
... if i == 10:
... break
... print i, string
... i += 1
...
1 A
2 B
3 C
4 A
5 B
6 C
7 A
8 B
9 C

repeat

repeat() 用于反复生成一个 object:

>>> import itertools
>>>
>>> for item in itertools.repeat('hello world', 3):
... print item
...
hello world
hello world
hello world
>>>
>>> for item in itertools.repeat([1, 2, 3, 4], 3):
... print item
...
[1, 2, 3, 4]
[1, 2, 3, 4]
[1, 2, 3, 4]

有限迭代器

itertools 模块提供了多个函数(类),接收一个或多个迭代对象作为参数,对它们进行组合、分组和过滤等:

chain()

compress()

dropwhile()

groupby()

ifilter()

ifilterfalse()

islice()

imap()

starmap()

tee()

takewhile()

izip()

izip_longest()

chain

chain 的使用形式如下:

chain(iterable1, iterable2, iterable3, ...)

chain 接收多个可迭代对象作为参数,将它们『连接』起来,作为一个新的迭代器返回。

>>> from itertools import chain
>>>
>>> for item in chain([1, 2, 3], ['a', 'b', 'c']):
... print item
...
1
2
3
a
b
c

chain 还有一个常见的用法:

chain.from_iterable(iterable)

接收一个可迭代对象作为参数,返回一个迭代器:

>>> from itertools import chain
>>>
>>> string = chain.from_iterable('ABCD')
>>> string.next()
'A'

compress

compress 的使用形式如下:

compress(data, selectors)

compress 可用于对数据进行筛选,当 selectors 的某个元素为 true 时,则保留 data 对应位置的元素,否则去除:

>>> from itertools import compress
>>>
>>> list(compress('ABCDEF', [1, 1, 0, 1, 0, 1]))
['A', 'B', 'D', 'F']
>>> list(compress('ABCDEF', [1, 1, 0, 1]))
['A', 'B', 'D']
>>> list(compress('ABCDEF', [True, False, True]))
['A', 'C']

dropwhile

dropwhile 的使用形式如下:

dropwhile(predicate, iterable)

其中,predicate 是函数,iterable 是可迭代对象。对于 iterable 中的元素,如果 predicate(item) 为 true,则丢弃该元素,否则返回该项及所有后续项。

>>> from itertools import dropwhile
>>>
>>> list(dropwhile(lambda x: x < 5, [1, 3, 6, 2, 1]))
[6, 2, 1]
>>>
>>> list(dropwhile(lambda x: x > 3, [2, 1, 6, 5, 4]))
[2, 1, 6, 5, 4]

groupby

groupby 用于对序列进行分组,它的使用形式如下:

groupby(iterable[, keyfunc])

其中,iterable 是一个可迭代对象,keyfunc 是分组函数,用于对 iterable 的连续项进行分组,如果不指定,则默认对 iterable 中的连续相同项进行分组,返回一个 (key, sub-iterator) 的迭代器。

>>> from itertools import groupby
>>>
>>> for key, value_iter in groupby('aaabbbaaccd'):
... print key, ':', list(value_iter)
...
a : ['a', 'a', 'a']
b : ['b', 'b', 'b']
a : ['a', 'a']
c : ['c', 'c']
d : ['d']
>>>
>>> data = ['a', 'bb', 'ccc', 'dd', 'eee', 'f']
>>> for key, value_iter in groupby(data, len): # 使用 len 函数作为分组函数
... print key, ':', list(value_iter)
...
1 : ['a']
2 : ['bb']
3 : ['ccc']
2 : ['dd']
3 : ['eee']
1 : ['f']
>>>
>>> data = ['a', 'bb', 'cc', 'ddd', 'eee', 'f']
>>> for key, value_iter in groupby(data, len):
... print key, ':', list(value_iter)
...
1 : ['a']
2 : ['bb', 'cc']
3 : ['ddd', 'eee']
1 : ['f']

ifilter

ifilter 的使用形式如下:

ifilter(function or None, sequence)

将 iterable 中 function(item) 为 True 的元素组成一个迭代器返回,如果 function 是 None,则返回 iterable 中所有计算为 True 的项。

>>> from itertools import ifilter
>>>
>>> list(ifilter(lambda x: x < 6, range(10)))
[0, 1, 2, 3, 4, 5]
>>>
>>> list(ifilter(None, [0, 1, 2, 0, 3, 4]))
[1, 2, 3, 4]

ifilterfalse

ifilterfalse 的使用形式和 ifilter 类似,它将 iterable 中 function(item) 为 False 的元素组成一个迭代器返回,如果 function 是 None,则返回 iterable 中所有计算为 False 的项。

>>> from itertools import ifilterfalse
>>>
>>> list(ifilterfalse(lambda x: x < 6, range(10)))
[6, 7, 8, 9]
>>>
>>> list(ifilter(None, [0, 1, 2, 0, 3, 4]))
[0, 0]

islice

islice 是切片选择,它的使用形式如下:

islice(iterable, [start,] stop [, step])

其中,iterable 是可迭代对象,start 是开始索引,stop 是结束索引,step 是步长,start 和 step 可选。

>>> from itertools import count, islice
>>>
>>> list(islice([10, 6, 2, 8, 1, 3, 9], 5))
[10, 6, 2, 8, 1]
>>>
>>> list(islice(count(), 6))
[0, 1, 2, 3, 4, 5]
>>>
>>> list(islice(count(), 3, 10))
[3, 4, 5, 6, 7, 8, 9]
>>> list(islice(count(), 3, 10 ,2))
[3, 5, 7, 9]

imap

imap 类似 map 操作,它的使用形式如下:

imap(func, iter1, iter2, iter3, ...)

imap 返回一个迭代器,元素为 func(i1, i2, i3, ...),i1,i2 等分别来源于 iter, iter2。

>>> from itertools import imap
>>>
>>> imap(str, [1, 2, 3, 4])
<itertools.imap object at 0x10556d050>
>>>
>>> list(imap(str, [1, 2, 3, 4]))
['1', '2', '3', '4']
>>>
>>> list(imap(pow, [2, 3, 10], [4, 2, 3]))
[16, 9, 1000]

itertools.starmap(function, iterable)

创建一个迭代器,生成值func(*item),其中item来自iterable,只有当iterable生成的项适用于这种调用函数的方式时,此函数才有效。

对序列seq的每个元素作为func的参数列表执行, 返回执行结果的迭代器

from itertools import *
values = [(0, 5), (1, 6), (2, 7), (3, 8), (4, 9)]
for i in starmap(lambda x,y:(x, y, x*y), values):
print '%d * %d = %d' % i
0 * 5 = 0
1 * 6 = 6
2 * 7 = 14
3 * 8 = 24
4 * 9 = 36

tee

tee 的使用形式如下:

tee(iterable [,n])

tee 用于从 iterable 创建 n 个独立的迭代器,以元组的形式返回,n 的默认值是 2。

>>> from itertools import tee
>>>
>>> tee('abcd') # n 默认为 2,创建两个独立的迭代器
(<itertools.tee object at 0x1049957e8>, <itertools.tee object at 0x104995878>)
>>>
>>> iter1, iter2 = tee('abcde')
>>> list(iter1)
['a', 'b', 'c', 'd', 'e']
>>> list(iter2)
['a', 'b', 'c', 'd', 'e']
>>>
>>> tee('abc', 3) # 创建三个独立的迭代器
(<itertools.tee object at 0x104995998>, <itertools.tee object at 0x1049959e0>, <itertools.tee object at 0x104995a28>)

takewhile

takewhile 的使用形式如下:

takewhile(predicate, iterable)

其中,predicate 是函数,iterable 是可迭代对象。对于 iterable 中的元素,如果 predicate(item) 为 true,则保留该元素,只要 predicate(item) 为 false,则立即停止迭代。

>>> from itertools import takewhile
>>>
>>> list(takewhile(lambda x: x < 5, [1, 3, 6, 2, 1]))
[1, 3]
>>> list(takewhile(lambda x: x > 3, [2, 1, 6, 5, 4]))
[]

izip

izip 用于将多个可迭代对象对应位置的元素作为一个元组,将所有元组『组成』一个迭代器,并返回。它的使用形式如下:

izip(iter1, iter2, ..., iterN)

如果某个可迭代对象不再生成值,则迭代停止。

>>> from itertools import izip
>>>
>>> for item in izip('ABCD', 'xy'):
... print item
...
('A', 'x')
('B', 'y')
>>> for item in izip([1, 2, 3], ['a', 'b', 'c', 'd', 'e']):
... print item
...
(1, 'a')
(2, 'b')
(3, 'c')

izip_longest

izip_longest 跟 izip 类似,但迭代过程会持续到所有可迭代对象的元素都被迭代完。它的形式如下:

izip_longest(iter1, iter2, ..., iterN, [fillvalue=None])

如果有指定 fillvalue,则会用其填充缺失的值,否则为 None。

>>> from itertools import izip_longest
>>>
>>> for item in izip_longest('ABCD', 'xy'):
... print item
...
('A', 'x')
('B', 'y')
('C', None)
('D', None)
>>>
>>> for item in izip_longest('ABCD', 'xy', fillvalue='-'):
... print item
...
('A', 'x')
('B', 'y')
('C', '-')
('D', '-')

组合生成器

itertools 模块还提供了多个组合生成器函数,用于求序列的排列、组合等:

product

permutations

combinations

combinations_with_replacement

product

product 用于求多个可迭代对象的笛卡尔积,它跟嵌套的 for 循环等价。它的一般使用形式如下:

product(iter1, iter2, ... iterN, [repeat=1])
其中,repeat 是一个关键字参数,用于指定重复生成序列的次数,
>>> from itertools import product
>>>
>>> for item in product('ABCD', 'xy'):
... print item
...
('A', 'x')
('A', 'y')
('B', 'x')
('B', 'y')
('C', 'x')
('C', 'y')
('D', 'x')
('D', 'y')
>>>
>>> list(product('ab', range(3)))
[('a', 0), ('a', 1), ('a', 2), ('b', 0), ('b', 1), ('b', 2)]
>>>
>>> list(product((0,1), (0,1), (0,1)))
[(0, 0, 0), (0, 0, 1), (0, 1, 0), (0, 1, 1), (1, 0, 0), (1, 0, 1), (1, 1, 0), (1, 1, 1)]
>>>
>>> list(product('ABC', repeat=2))
[('A', 'A'), ('A', 'B'), ('A', 'C'), ('B', 'A'), ('B', 'B'), ('B', 'C'), ('C', 'A'), ('C', 'B'), ('C', 'C')]
>>>

permutations

permutations 用于生成一个排列,它的一般使用形式如下:

permutations(iterable[, r])
其中,r 指定生成排列的元素的长度,如果不指定,则默认为可迭代对象的元素长度。
>>> from itertools import permutations
>>>
>>> permutations('ABC', 2)
<itertools.permutations object at 0x1074d9c50>
>>>
>>> list(permutations('ABC', 2))
[('A', 'B'), ('A', 'C'), ('B', 'A'), ('B', 'C'), ('C', 'A'), ('C', 'B')]
>>>
>>> list(permutations('ABC'))
[('A', 'B', 'C'), ('A', 'C', 'B'), ('B', 'A', 'C'), ('B', 'C', 'A'), ('C', 'A', 'B'), ('C', 'B', 'A')]
>>>

combinations

combinations 用于求序列的组合,它的使用形式如下:

combinations(iterable, r)
其中,r 指定生成组合的元素的长度
>>> from itertools import combinations
>>>
>>> list(combinations('ABC', 2))
[('A', 'B'), ('A', 'C'), ('B', 'C')]

combinations_with_replacement

combinations_with_replacement 和 combinations 类似,但它生成的组合包含自身元素。

>>> from itertools import combinations_with_replacement
>>>
>>> list(combinations_with_replacement('ABC', 2))
[('A', 'A'), ('A', 'B'), ('A', 'C'), ('B', 'B'), ('B', 'C'), ('C', 'C')]

扩展,使用现有扩展功能

def take(n, iterable):
"Return first n items of the iterable as a list"
return list(islice(iterable, n))
def tabulate(function, start=0):
"Return function(0), function(1), ..."
return imap(function, count(start))
def consume(iterator, n):
"Advance the iterator n-steps ahead. If n is none, consume entirely."
# Use functions that consume iterators at C speed.
if n is None:
# feed the entire iterator into a zero-length deque
collections.deque(iterator, maxlen=0)
else:
# advance to the empty slice starting at position n
next(islice(iterator, n, n), None)
def nth(iterable, n, default=None):
"Returns the nth item or a default value"
return next(islice(iterable, n, None), default)
def quantify(iterable, pred=bool):
"Count how many times the predicate is true"
return sum(imap(pred, iterable))
def padnone(iterable):
"""Returns the sequence elements and then returns None indefinitely.
Useful for emulating the behavior of the built-in map() function.
"""
return chain(iterable, repeat(None))
def ncycles(iterable, n):
"Returns the sequence elements n times"
return chain.from_iterable(repeat(tuple(iterable), n))
def dotproduct(vec1, vec2):
return sum(imap(operator.mul, vec1, vec2))
def flatten(listOfLists):
"Flatten one level of nesting"
return chain.from_iterable(listOfLists)
def repeatfunc(func, times=None, *args):
"""Repeat calls to func with specified arguments.
Example: repeatfunc(random.random)
"""
if times is None:
return starmap(func, repeat(args))
return starmap(func, repeat(args, times))
def pairwise(iterable):
"s -> (s0,s1), (s1,s2), (s2, s3), ..."
a, b = tee(iterable)
next(b, None)
return izip(a, b)
def grouper(iterable, n, fillvalue=None):
"Collect data into fixed-length chunks or blocks"
# grouper('ABCDEFG', 3, 'x') --> ABC DEF Gxx
args = [iter(iterable)] * n
return izip_longest(fillvalue=fillvalue, *args)
def roundrobin(*iterables):
"roundrobin('ABC', 'D', 'EF') --> A D E B F C"
# Recipe credited to George Sakkis
pending = len(iterables)
nexts = cycle(iter(it).next for it in iterables)
while pending:
try:
for next in nexts:
yield next()
except StopIteration:
pending -= 1
nexts = cycle(islice(nexts, pending))
def powerset(iterable):
"powerset([1,2,3]) --> () (1,) (2,) (3,) (1,2) (1,3) (2,3) (1,2,3)"
s = list(iterable)
return chain.from_iterable(combinations(s, r) for r in range(len(s)+1))
def unique_everseen(iterable, key=None):
"List unique elements, preserving order. Remember all elements ever seen."
# unique_everseen('AAAABBBCCDAABBB') --> A B C D
# unique_everseen('ABBCcAD', str.lower) --> A B C D
seen = set()
seen_add = seen.add
if key is None:
for element in ifilterfalse(seen.__contains__, iterable):
seen_add(element)
yield element
else:
for element in iterable:
k = key(element)
if k not in seen:
seen_add(k)
yield element
def unique_justseen(iterable, key=None):
"List unique elements, preserving order. Remember only the element just seen."
# unique_justseen('AAAABBBCCDAABBB') --> A B C D A B
# unique_justseen('ABBCcAD', str.lower) --> A B C A D
return imap(next, imap(itemgetter(1), groupby(iterable, key)))
def iter_except(func, exception, first=None):
""" Call a function repeatedly until an exception is raised.
Converts a call-until-exception interface to an iterator interface.
Like __builtin__.iter(func, sentinel) but uses an exception instead
of a sentinel to end the loop.
Examples:
bsddbiter = iter_except(db.next, bsddb.error, db.first)
heapiter = iter_except(functools.partial(heappop, h), IndexError)
dictiter = iter_except(d.popitem, KeyError)
dequeiter = iter_except(d.popleft, IndexError)
queueiter = iter_except(q.get_nowait, Queue.Empty)
setiter = iter_except(s.pop, KeyError)
"""
try:
if first is not None:
yield first()
while 1:
yield func()
except exception:
pass
def random_product(*args, **kwds):
"Random selection from itertools.product(*args, **kwds)"
pools = map(tuple, args) * kwds.get('repeat', 1)
return tuple(random.choice(pool) for pool in pools)
def random_permutation(iterable, r=None):
"Random selection from itertools.permutations(iterable, r)"
pool = tuple(iterable)
r = len(pool) if r is None else r
return tuple(random.sample(pool, r))
def random_combination(iterable, r):
"Random selection from itertools.combinations(iterable, r)"
pool = tuple(iterable)
n = len(pool)
indices = sorted(random.sample(xrange(n), r))
return tuple(pool[i] for i in indices)
def random_combination_with_replacement(iterable, r):
"Random selection from itertools.combinations_with_replacement(iterable, r)"
pool = tuple(iterable)
n = len(pool)
indices = sorted(random.randrange(n) for i in xrange(r))
return tuple(pool[i] for i in indices)
def tee_lookahead(t, i):
"""Inspect the i-th upcomping value from a tee object
while leaving the tee object at its current position.
Raise an IndexError if the underlying iterator doesn't
have enough values.
"""
for value in islice(t.__copy__(), i, None):
return value
raise IndexError(i)

自定义扩展,将序列按大小切分,更好的性能

from itertools import chain, islice
def chunks(iterable, size, format=iter):
it = iter(iterable)
while True:
yield format(chain((it.next(),), islice(it, size - 1)))
>>> l = ["a", "b", "c", "d", "e", "f", "g"]
>>> for chunk in chunks(l, 3, tuple):...
print chunk...
("a", "b", "c")
("d", "e", "f")
("g",)

itertools 模块提供了很多用于产生多种类型迭代器的函数,它们的返回值不是 list,而是迭代器

迭代工具,你最好的朋友

迭代工具模块包含了操做指定的函数用于操作迭代器。想复制一个迭代器出来?链接两个迭代器?以one liner(这里的one-liner只需一行代码能搞定的任务)用内嵌的列表组合一组值?不使用list创建Map/Zip?···,你要做的就是 import itertools,举个例子吧:

四匹马赛跑到达终点排名的所有可能性:

>>> horses = [1, 2, 3, 4]
>>> races = itertools.permutations(horses)
>>> print(races)
<itertools.permutations object at 0xb754f1dc]]>
>>> print(list(itertools.permutations(horses)))
[(1, 2, 3, 4),
(1, 2, 4, 3),
(1, 3, 2, 4),
(1, 3, 4, 2),
(1, 4, 2, 3),
(1, 4, 3, 2),
(2, 1, 3, 4),
(2, 1, 4, 3),
(2, 3, 1, 4),
(2, 3, 4, 1),
(2, 4, 1, 3),
(2, 4, 3, 1),
(3, 1, 2, 4),
(3, 1, 4, 2),
(3, 2, 1, 4),
(3, 2, 4, 1),
(3, 4, 1, 2),
(3, 4, 2, 1),
(4, 1, 2, 3),
(4, 1, 3, 2),
(4, 2, 1, 3),
(4, 2, 3, 1),
(4, 3, 1, 2),
(4, 3, 2, 1)]

理解迭代的内部机制: 迭代(iteration)就是对可迭代对象(iterables,实现了__iter__()方法)和迭代器(iterators,实现了__next__()方法)的一个操作过程。可迭代对象是任何可返回一个迭代器的对象,迭代器是应用在迭代对象中迭代的对象,换一种方式说的话就是:iterable对象的__iter__()方法可以返回iterator对象,iterator通过调用next()方法获取其中的每一个值(译者注),读者可以结合Java API中的 Iterable接口和Iterator接口进行类比。

高效的 itertools 模块(转)的更多相关文章

  1. PYTHON-进阶-ITERTOOLS模块

    PYTHON-进阶-ITERTOOLS模块小结 这货很强大, 必须掌握 文档 链接 pymotw 链接 基本是基于文档的翻译和补充,相当于翻译了 itertools用于高效循环的迭代函数集合 组成 总 ...

  2. python itertools 模块讲解

    1.介绍itertools 是python的迭代器模块,itertools提供的工具相当高效且节省内存. 使用这些工具,你将能够创建自己定制的迭代器用于高效率的循环. - 无限迭代器 itertool ...

  3. Python标准库笔记(10) — itertools模块

    itertools 用于更高效地创建迭代器的函数工具. itertools 提供的功能受Clojure,Haskell,APL和SML等函数式编程语言的类似功能的启发.它们的目的是快速有效地使用内存, ...

  4. itertools模块

    itertools模块中有很多函数,返回的是一个迭代器 参考: http://www.wklken.me/posts/2013/08/20/python-extra-itertools.html#_1

  5. 转:Python itertools模块

    itertools Python的内建模块itertools提供了非常有用的用于操作迭代对象的函数. 首先,我们看看itertools提供的几个"无限"迭代器: >>& ...

  6. python, itertools模块

    通过itertools模块,可以用各种方式对数据进行循环操作 1, chain() from intertools import chain for i in chain([1,2,3], ('a', ...

  7. itertools模块速查

    学习itertools模块记住这张表就OK了 参考:http://docs.python.org/2/library/itertools.html#module-itertools Infinite ...

  8. Python中itertools模块

    itertools模块包含创建有效迭代器的函数,可以用各种方式对数据进行循环操作,此模块中的所有函数返回的迭代器都可以与for循环语句以及其他包含迭代器(如生成器和生成器表达式)的函数联合使用. ch ...

  9. Python:itertools模块

    itertools模块包含创建有效迭代器的函数,可以用各种方式对数据进行循环操作,此模块中的所有函数返回的迭代器都可以与for循环语句以及其他包含迭代器(如生成器和生成器表达式)的函数联合使用. ch ...

随机推荐

  1. CCD和CMOS的差别

    单从感光器电子技术上来说,CCD比CMOS更先进,理论成像上有优势,但是最近几年CMOS却发展更好,使得很多高端数码单反采用CMOS传感器,下面来看看CCD和CMOS的技术知识: CCD和CMOS传感 ...

  2. 面试精选之Promise

    常见Promise面试题 我们看一些 Promise 的常见面试问法,由浅至深. 1.了解 Promise 吗? 2.Promise 解决的痛点是什么? 3.Promise 解决的痛点还有其他方法可以 ...

  3. dot.js使用心得

    一.dot.js介绍 最近用到的数据模板引擎有很多,今天讲的doT.js也是其中一种. doT.js的特点是体积小,速度快,并且不依赖其他插件. 官网下载:http://olado.github.io ...

  4. bzoj 1296 DP

    对于每一行做DP预处理,w[i][j]代表这一行前i个刷j次的最大价值,那么w[i][j]=max(w[i][j],w[k][j-1]+sum[k+1][i]),sum[i][j]为i-j段刷一次最多 ...

  5. js_判断当前页面是否有网络和网络连接超时

    2018-04-12 方法一:通过navigator.onLine属性判断,返回true为有联网状态,false为断网状态. //方法一 if(navigator.onLine) { console. ...

  6. 概率DP入门学习QAQ

    emmmm博客很多都烂尾了...但是没空写..先写一下正在学的东西好了 概率DP这东西每次考到都不会..听题解也是一脸懵逼..所以决定学习一下这个东东..毕竟NOIP考过...比什么平衡树实在多了QA ...

  7. python中requests库中文乱码问题

    当使用这个库的时候经常会出现各种乱码的情况. 首先要知道: text返回的是处理过的unicode的数据. content返回的是bytes的原始数据 也就是说r.content比r.text更加节省 ...

  8. Vuex 基本概念

    Vuex 是一个专为 Vue.js 应用程序开发的状态管理模式.它采用集中式存储管理应用的所有组件的状态,并以相应的规则保证状态以一种可预测的方式发生变化. 每一个 Vuex 应用的核心就是 stor ...

  9. Linux配置Tomcat

    系统:Ubuntu,Tomcat:apache-tomcat-8.5.23.tar.gz 1,找到apache-tomcat-8.5.23.tar.gz,复制到 /usr/local root@ubu ...

  10. Every Tom,Dick and Harry. 不管张三李四。

    1 every  adj   每个,最大的,所有的,一切的 Every other girl except me is wearing jeans.  除了我之外的每个女孩都穿着牛仔裤. I have ...