2016-09-17 506 views
1

我是一个新手Python学生,我正在经历一些简单的(但现在,对我来说,复杂的)练习。我尝试了很多方法,但我决定停止猜测,因为我相信这不是一个理智的学习过程。Python练习:最后一个字母/第一个字母

我必须解决以下练习:

lastfirst(lst)功能,即,给定一个列表,返回的是一个不同的角色开始从的的 最后一个字符列表中的 第一个字前一个词。如果没有这样的词, 返回None

例子:

lst = ['sole','elmo','orco','alba','asta']回报'alba'

lst = ['sky','you','use','ear','right']返回None

我试图解决它,我曾是这样的:

lst = ['sole','elmo','orco','alba','asta'] 

def lastfirst(lst): 

    cont = 0 
    d = 1 
    for a in lst[cont:]: 
     for b in lst[d:]:  
      if a[-1] != b[0]: 
       return lst[d] 
      else: 
       cont = cont + 1 
       d = d + 1 

print(lastfirst(lst)) 

问题我检测到的是:

该程序不区分第一个单词的第一个字母和第二个单词的最后一个字母,或第一个单词的最后一个字母和第二个单词的第一个字母。

PS:对不起,我的英语:)

+0

'lst [i] [ - 1]'表示获得'lst'的项目'i',然后获得_that_项目的最后一项。所以如果'lst = ['sky','you','use','ear','right']',那么'lst [2]'是''use'',并且lst [2] [ - 1] ''''''''''''',是'use'的最后一个字母。 –

+0

非常感谢! :) – Nutshell93

+0

如果其中一个答案解决了您的问题,您应该接受它(单击相应答案旁边的复选标记)。这有两件事。它让每个人都知道你的问题已经得到解决,让你满意,并且它可以帮助你帮助你。请参阅[此处](http://meta.stackexchange.com/a/5235)以获取完整说明。 –

回答

2

我认为它会工作(在Python 3):

lst = ['sole','elmo','orco','alba','asta'] 

def lastfirst(lst): 
    for i in range(len(lst)-1): 
     if lst[i][-1] != lst[i+1][0] : 
      return lst[i+1] 
    return None 
print(lastfirst(lst)) 

输出

alba 

解释(无需修改在你的代码中):

  • 我们不需要两个for循环,我们可以在for循环中做到这一点。
  • 尽管您在else声明中增加了cont变量,但它总是会将其与a中的相同字符串进行比较。

其他输入:

lst = ['sky','you','use','ear','right'] 

输出:

None 

希望它会帮助你。

+0

@PM 2Ring我知道,但我有习惯,因为'C++'。我会更新..谢谢反正。 –

+0

非常感谢你! – Nutshell93

1

当你需要测试的每一个字在lst对所有其他字lst,但是这不是我们想在这里你会使用双for循环。我们只需要一个for循环,我们需要存储前一个单词,以便我们可以对当前单词进行测试。就像这样:

def lastfirst(lst): 
    if not lst: 
     return None 
    prev = lst[0] 
    for word in lst[1:]: 
     if word[0] != prev[-1]: 
      return word 
     prev = word 
    return None 


data = [ 
    ['sole', 'elmo', 'orco', 'alba', 'asta'], 
    ['sky', 'you', 'use', 'ear', 'right'], 
    [], 
    ['help', 'please', 'everybody', 'thanks'], 
] 

for lst in data: 
    print(lastfirst(lst)) 

输出

alba 
None 
None 
thanks 

我的函数首先做

if not lst: 
    return None 

,所以我们立即返回,如果我们获得通过一个空列表。否则,程序会在尝试做prev = lst[0]


崩溃下面是一个有效的方法做测试用的单行。

def lastfirst(lst): 
    return next((v for u, v in zip(lst, lst[1:]) if u[-1] != v[0]), None) 

这段代码比我以前的版本显然更紧凑,而且可能快一点。但它难以理解,特别是如果你是新手到Python。有些人认为像这样的“单线”更多是Pythonic,但实际上让代码尽可能易读是更为Pythonic。 :)

+0

“当你需要对第一个字中的每一个单词进行测试时,你会使用double for循环”。你的意思是像组合!? – Nutshell93

+0

@ Nutshell93:是的,如果你想用'lst'中的所有单词来做一些事情,你可以使用一个双'for'循环,而不是相邻的单词。但是,'itertools'模块可以使用一个'for'循环来创建各种组合和排列。 –

0

这是一个使用itertools的解决方案。

首先,定义返回如果条件得到满足的布尔函数:

def check_letters(apair): 
"In a pair, check last letter of first entry with first letter of second" 
    return apair[0][-1] == apair[1][0] 

现在我们使用成对的函数从itertools module食谱:

import itertools 
def pairwise(iterable): 
    "s -> (s0,s1), (s1,s2), (s2, s3), ..." 
    a, b = itertools.tee(iterable) 
    next(b, None) 
    return itertools.izip(a, b) 

最后:

lst = ['sole','elmo','orco','alba','asta'] 
lstlast = [item[1] for item in pairwise(lst) if not check_letters(item)] 
# returns ['alba'] 
+0

非常感谢你! – Nutshell93

相关问题