Python中C语言编程技巧的等效方法(while循环)
在C语言中,我经常会做以下操作:
while ((c = getch()) != EOF) {
/* do something with c */
}
在Python中,我没有找到类似的东西,因为我不能在被计算的表达式里面设置变量。结果我通常得把被计算的表达式写两遍!
c = sys.stdin.read(1)
while not (c == EOF):
# Do something with c
c = sys.stdin.read(1)
为了找到更好的方法,我发现了一种只需要设置一次被计算表达式的方法,但这看起来越来越复杂了...
while True:
c = sys.stdin.read(1)
if (c == EOF): break
# do stuff with c
到目前为止,我在某些情况下采用了以下方法,但对于普通的while循环来说,这远不是最佳选择...:
class ConditionalFileObjectReader:
def __init__(self,fobj, filterfunc):
self.filterfunc = filterfunc
self.fobj = fobj
def __iter__(self):
return self
def next(self):
c = self.fobj.read(1)
if self.filterfunc(c): raise StopIteration
return c
for c in ConditionalFileObjectReader(sys.stdin,lambda c: c == EOF):
print c
我解决一个简单的编程问题的方法变得太复杂了... 有没有人能给我一些建议,教我怎么正确地做这件事?
3 个回答
你可以用更简单的代码来替代你的ConditionalFileObjectReader,因为看起来你最关心的是文件的结束标志(EOF),而不是其他什么条件:
def readbytes(file):
while True:
c = file.read(1)
if c == '':
return
yield c
for c in readbytes(sys.stdin):
print c
所以你还是用到了'while True ... break',这在Python中似乎是比较常用的循环方式[*],不过至少你只需要写一次就能解决“如何遍历一个类似文件的对象中的字节,而不需要逐行阻塞或缓冲”的问题,而且这个循环很简短,不会对'c'做什么操作——那是另外一个问题。
受到Wallacoloo的例子启发,使用iter
,你可以做出比iter
更通用的东西,类似于上面的代码:
def until(nextvalue, pred):
while True:
value = nextvalue()
if pred(value):
return
yield value
for c in until(lambda: sys.stdin.read(1), lambda x: x == ''):
print c
我不太确定我是否喜欢这个,但可能值得尝试一下。它试图解决一个更普遍的问题:“遍历某个函数的返回值,直到返回值满足某个条件”。
[*] 我敢说,这在Python中相当于其他语言中复杂循环语法的简化版吗?
在Python中,你通常会使用一个for
循环:
for c in sys.stdin.read():
# whatever
如果你不想一次性把所有输入都放到内存里,你也可以自己设置一个小一点的缓冲区来进行一些缓冲。
需要注意的是,常量EOF
在Python中是不存在的。如果流中没有数据了,read()
会直接返回一个空字符串。
我觉得你想做的事情是使用 iter
这个函数。
for c in iter(getch, EOF):
#inner loop
iter 是一个非常灵活的函数。在这个例子中,你是在告诉它在每次循环的开始都要不断调用 getch
(不带任何参数),直到 getch
返回一个特殊的值,叫做 EOF。