如何表示动态范围列表?
在打印文档的页面时,比如说,你可以用一种简便的方式来指定你想打印的具体页码:
1, 3, 4-7, 9-
在一个有12页的文档中,这样的方式会打印出:
1, 3, 4, 5, 6, 7, 9, 10, 11, 12
我想知道如何在Python中表示这样的结构,这样我就可以查询某个特定的“页码”(这不仅限于打印;只是一个例子)是否在这个范围内,并且还能遍历这个范围。
如果这些页码是以简单的列表形式存在,就像第二个例子那样(把它转换成那样的字符串处理也很简单),那么这些事情就容易多了。但开放式的范围就带来了问题。在最后一刻之前,不能把它们简化成一个平坦的列表。
3 个回答
0
请原谅我这个新手的尝试,我用元组的列表来表示页面。
pages=[(1,1),(3,3),(4,7),(8,)]
def find_page(pages,page):
for p in pages:
if len(p)==1:
if page >= p[0]:
return True
else:
break
if p[0]==p[1]:
if page==p[0]:
return True
elif page >= p[0] and page <= p[1]:
return True
1
如果我理解你的问题没错的话,你可以使用一个包含元组的列表。比如说,(1,1)
表示第1页,(4, 7)
表示第4、5、6和7页。比较棘手的部分是如何表示“从这一页到最后一页”。不过,如果你知道总页数的话,可以用float("inf")
来解决这个问题。然后,扁平化的函数大概会是这样的:
def flatten_ranges(ranges, number_of_pages):
flattened_list = []
for item in ranges:
page = item[0]
while page <= item[1] and page <= number_of_pages:
flattened_list.append(page)
page += 1
return flattened_list
0
我会使用一个生成器:
import itertools
def parse_ranges(ranges):
for chunk in ranges.split(', '):
if '-' not in chunk:
chunk = chunk + '-' + chunk # Turns 7 into 7-7
start, end = chunk.split('-')
if end:
yield from range(int(start), int(end) + 1)
else:
yield from itertools.count(int(start))
在你遍历它的时候,可以限制最大页码:
for page in parse_ranges('1, 3, 4-7, 9-'):
if page > 20:
break
print(page)
或者单独处理这个问题:
def cap(iterable, maximum):
for n in iterable:
if n > maximum:
break
yield n
pages = list(cap(parse_ranges('1, 3, 4-7, 9-'), 20))