C编程技术的Python等价物(while循环)

C编程技术的Python等价物(while循环),python,c,Python,C,在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) 在我试图找到更好的方法的过程中,我找到了一种只需

在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
我所有解决一个简单的基本编程问题的方法都变得太复杂了。。。
有人建议如何正确地执行此操作吗?

您通常会在Python中使用
for
循环:

for c in sys.stdin.read():
    # whatever
如果您不想一次在内存中缓冲整个stdin,您也可以自己使用较小的缓冲区添加一些缓冲


请注意,Python中不存在常量
EOF
read()
如果流中没有留下任何数据,将只返回一个空字符串。

可以编写更简单的代码来代替ConditionalFileObjectReader,因为EOF似乎是您所关心的,而不是任意的条件:

def readbytes(file):
    while True:
        c = file.read(1)
        if c == '':
            return
        yield c

for c in readbytes(sys.stdin):
    print c
所以你还有“虽然是真的。。。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
我不确定我是否喜欢这个,但可能值得一玩。它试图解决一般问题“迭代某个函数的返回值,直到返回值满足某个条件”


[*]我敢说,在其他语言中,Pythonic相当于花式循环语法?

我相信你想做的是利用
iter
函数

for c in iter(getch, EOF):
     #inner loop

国际热核聚变实验堆(Iter)是一个非常通用的功能。在本例中,您告诉它在每个循环的顶部重复调用
getch
(无参数),直到
getch
返回sentinel值EOF。

很好,但这并不能解决python中while循环的基本问题。阅读stdin只是一个例子,说明了这个“问题”“狗吃猫世界:然后不要使用<代码>而<代码> >循环那些不需要代码的东西,而循环在Python中。@狗:<代码>而循环在Python中比在C.中更不常见,我个人认为在循环中环中的中断条件不太好,它们经常出现在C.It中,而不仅仅是一个问题。一次在内存中缓冲整个输入,
read
阻塞,直到有足够的数据可用或EOF。我们是否确定Python无法为流式I/O编写比
更好的循环,而这是真的。。。中断
?我个人可以接受,但我明白为什么人们可能更喜欢“更干净”的替代方案。@Dog你没有要求解决“python中while循环的基本缺点”。你要求“正确的方法”。有一个原因你不经常在Python中看到while循环:原因是它们很少是一种明显正确的方法。我发现:但遗憾的是,它还没有实现……非常类似于这个问题:你可能对我的答案感兴趣-有点相切,但仍然相关。谢谢,这也行得通。我用lambda:sys.stdin.read(1)替换了getch,但是这个问题是针对一般语法的,而不是针对这个特定的问题。但是我看到了在可能的情况下使用迭代器的意义:)@Brendan:这是
functools.partial()
,而且我认为它不会更快(没有测试)。哦。我的印象是,lambas在python中相当慢,因此
partial
可能更好。