# -*- coding: utf-8 -*-import requests
from collections import Iterable, Iterator
classWeatherIterator(Iterator):# 定義迭代器 def__init__(self, cities):
self.cities = cities
self.index = 0defget_weather(self,city):# 獲取天氣的數據
r = requests.get(u'http://wthrcdn.etouch.cn/weather_mini?city=' + city)
data = r.json()['data']['forecast'][0]
return'%s:%s,%s' % (city, data['low'], data['high'])
defnext(self):# 定義迭代器的next()方法if self.index == len(self.cities):
raise StopIteration # 如果全部迭代完的處理方法
city = self.cities[self.index]
self.index += 1return self.get_weather(city)
classWeatherIterable(Iterable):# 定義可迭代對象def__init__(self, cities):print' __init__'
self.cities = cities
def__iter__(self):print'__iter__'return WeatherIterator(self.cities) # 返回一個迭代器對象if __name__ == '__main__':
# for x in obj 循環的基本原理是,# obj是一個可迭代對象,for循環之前,先調用obj.__iter__方法,返回一個迭代器對象Iterator,迭代器對象通過nex()t方法,返回每個值# 要寫出自己的可迭代對象,需要繼承Iterable,__iter__()方法,並返回一個可迭代器對象# 在自己的迭代器對象中定義next()方法,通過next方法,獲取每次迭代的值
city_list = [u'深圳', u'北京', u'上海', u'廣州', u'青島', u'荊州', u'武漢']
for x in WeatherIterable(city_list):
print x
二、使用生成器函數實現可迭代對象
classPrimeNumber(object):def__init__(self, start, end):
self.start = start
self.end = end
defget_prime(self, k):# 判斷是否是素數,如果是,返回Trueif k < 2:
returnFalsefor x in xrange(2, k):
if k % x == 0:
returnFalsereturnTruedef__iter__(self):# for...in..循環時,先調用__iter__,返回一個迭代生成器對象print'__iter__'for x in xrange(self.start, self.end):
if self.get_prime(x):
# yield是一個關鍵詞,類似return, 不同之處在於,yield返回的是一個生成器對象,生成器每次調用next,返回一個xyield x
for x in PrimeNumber(0, 100):
print x
三、如何進行反向迭代及如何實現反向迭代
classFloatRange(object):def__init__(self, start, end, step=0.5):
self.start = start
self.end = end
self.step = step
def__iter__(self):# 定義正向迭代方法
t = self.start
while t <= self.end:
yield t
t += self.step
def__reversed__(self):# 定義反向迭代方法
t = self.end
while t >= self.start:
yield t
t -= self.step
for x in FloatRange(1, 4, 0.5): # 默認調用__iter__()print x, " ",
for x in reversed(FloatRange(1, 4, 0.5)): # 調用__reversed__()方法,進行反迭代print x, " ",
四、對迭代器做切片操作
from itertools import islice
# islice切片對象,可以對可迭代對象進行切片# islice(iterable, [start,] stop [, step]) --> islice object # 如果只有一個參數,表示從第一個開始第一個元素開始,如果想從某一個位置到最後,可以islice(iterable,40,None)方法
f=open('digital','r')
for x in islice(f,3,5,1):
print x,
五、在for中迭代多個可迭代對象
from random import randint
from itertools import chain
# 要求統計三科總成績
chinese = [randint(60, 100) for _ in xrange(40)]
math = [randint(60, 100) for _ in xrange(40)]
english = [randint(60, 100) for _ in xrange(40)]
total = [] # 總分列表for c, m, e in zip(chinese, math, english): # zip將三個可迭代對象合併成一個元組列表[(),()...],如果三個對象長度不同,以最小的爲準
total.append(c + m + e)
print total
# 要求統三個班90分以上人數
c1 = [randint(60, 100) for _ in xrange(40)]
c2 = [randint(60, 100) for _ in xrange(45)]
c3 = [randint(60, 100) for _ in xrange(32)]
total = 0for x in chain(c1, c2, c3): # chain 將多個可迭代對象串聯成一個可迭代對象if x > 90:
total += 1