【问题标题】:How to use iterators in python [closed]如何在python中使用迭代器[关闭]
【发布时间】:2012-10-30 17:05:57
【问题描述】:

我正在学习 Python,但我不明白如何使用迭代器。

我需要编写代码。在 C 中它会是这样的:

list_node *cp = list_of_chars;
char dp = '>'; int flag = 0;
while (cp != NULL)
{ if( isdigit(cp->val) ) 
  { printf("%c",cp->val);
    if( cp->val == '0' )
    { cp->prev->next = cp->next; cp->next->prev = cp->prev; }
    else cp->val--;
  }
  else if( (cp->val == '>') || (cp->val == '<') )
  { dp = cp->val; flag = 1; }

       if( dp == '>' ) cp = cp->next;
  else if( dp == '<' ) cp = cp->prev;
  else return ERR;

  if( flag && ( (cp->val == '>') || (cp->val == '<') ))
  { cp->prev->prev->next = cp;
    cp->prev = cp->prev->prev;
  }
}

你能帮我把这段代码翻译成python吗?我开始写,但有一些错误,我不确定我是否理解文档。

  ip = {'cp' : iter(program), 'dp' : '>'}
  flag = 0

  while ip['cp'] != []:

    if ('0' <= ip['cp']) & (ip['cp'] <= '9'):
      print ip['cp']
      if ip['cp'] == '0': ip['cp']  = []
      else:               ip['cp'] -= 1

    elif (ip['cp'] == '>') | (ip['cp'] == '<'):
      ip['dp'] = ip.['cp']
      flag = 1

    else: raise NameError('incorrect cp-value')

    if   ip['dp'] == '>': ip['cp'].next()
    elif ip['dp'] == '<': ip['cp'].prev()
    else: raise NameError('incorrect dp-value')

    if flag & ( (ip['cp'] == '>') | (ip['cp'] == '<') ):
      ip['cp'].prev()
      ip['cp'] = []

问题是如何在没有函数 next() 的情况下获取迭代器的值。

具有高级迭代器使用的 python 专家代码示例也很高兴看到。

【问题讨论】:

  • 试图将 C 直接翻译成 Python 是一个糟糕的主意。您需要翻译概念,而不是代码。 Python 是一种更高级别的语言,它以 C 语言的方式做事,而在 Python 中,会产生可怕的、非 Python 的代码。
  • 我知道 C-prog.lang。并考虑一下。我试着向你解释我需要什么,并使用 C 语言。我无法用另一种方式解释算法。
  • @so-olitary 那么你的问题是你不能很好地定义问题。你需要给我们一个确切的问题。你在这里说它不起作用 - 这不够具体。你得到什么错误?有什么问题?
  • 您的 C 代码中似乎缺少 NULL 检查(当您从列表中删除节点时,请推进指针)。能否提供an example input such as 234&lt;5&gt;6 and the expected output e.g., 234321flag 只设置一次是否正确?不应该在循环内的某个点设置为零吗?
  • @J.F.塞巴斯蒂安 是的,我有所有的缺点。但是我没有为编译器编写代码。我试图解释算法。感谢您的更正和您的 python-code 示例。

标签: python string list iteration


【解决方案1】:

Python 中的迭代器只能前进。它们唯一支持的操作是 next(),它要么返回下一个值,要么引发 StopIteration 异常。它们不适合这个问题,你需要前进和后退。

您的原始代码令人困惑,但我会在 Python 中使用列表和整数索引来解决这个问题。

【讨论】:

【解决方案2】:

好的,你的python代码有很多问题。

从简单的开始

while ip['cp'] != []:

可以写成简单的

while ip['cp']:

ip['cp'] 不是一个错误的值时,它会起作用。例如,[], None, '' 是一个错误的值。

代替:

if   ip['dp'] == '>': ip['cp'].next()
elif ip['dp'] == '<': ip['cp'].prev()
else: raise NameError('incorrect dp-value')

if ip['dp'] == '>': 
    ip['cp'].next()
elif ip['dp'] == '<':
    ip['cp'].prev()
else: 
    raise NameError('incorrect dp-value')

即使在某些情况下,编写内联代码也是可行的。考虑可读性。内联代码几乎从来都不是让代码可读和易于调试的好开始。它还可以让您轻松修复 90% 的语法错误。

这里是乐趣的开始......

  if( cp->val == '0' )
  { cp->prev->next = cp->next; cp->next->prev = cp->prev; }
  else cp->val--;

  if ip['cp'] == '0': ip['cp']  = []
  else:               ip['cp'] -= 1

在 python 中,'0' 是字符串 0。在 python 中,当你有一个字符串对象时,你正在使用字符串。当你有数字时,你正在使用数字......换句话说,你试图用 python 编写的代码不能纯粹翻译成 python。 python 字符串中的最后一个字符不是'\0'。它是字符串中的最后一个字符。换句话说,你真的可以像在 C 中那样测试最后一个字符。

现在让我们谈谈迭代器

也就是说,忽略代码中的所有其他问题,以下是使用迭代器的方法。

iter() 是一个返回迭代器的内置函数。在大多数情况下,您不必自己调用它。有些结构可以为您做到这一点。

例如,你可以写:

iterable = iter('string')
iterable.next() == 's'
iterable.next() == 't'
... Until StopIteration is raised

for i in iter('string'):

等同于:

for i in 'string':

也就是说,迭代器用于迭代某些东西。您真正要寻找的不是迭代器。因为迭代器是一种方式。你可以走到尽头,你不能回去。没有以前的。您的 C 代码实现了一个可与迭代一起使用的链表,但在您的代码中,您正在更改某些节点的位置。

如果要写python代码,不要在python中写C代码

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-06-04
    • 1970-01-01
    • 2019-03-06
    • 2020-07-11
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多