使用Python列表的条件语句

1 投票
3 回答
3311 浏览
提问于 2025-04-16 06:02

我正在学习Python中的列表。在这段代码中,我想把从表单中得到的字符串s添加到表格的行里,只要这个字符串是相同的。当字符串不同时,新的字符串就会写到下一个列里。

我可以把字符串从column 0写到column 1,但在正确地把相同的字符串添加到column 1时遇到了问题。

现在的情况是,脚本只能把不同的字符串放到下一个列里。

我意识到这样做并不对。

我会很感激任何帮助。谢谢。我也附上了模板。

编辑2

@JerseyMike:谢谢你的回答。我还不太明白AddString(str)是怎么工作的,但在IDLE中尝试时,我注意到它不是添加新的字符串,而是用新的字符串替换了它。正如我所说,我还没有研究它是怎么工作的;但这是结果(我把str改成了str1):

>>> def AddString(str1):
    try:
        idx = map(lambda (s, v): ('N', 'Y')[s == str1], L).index('Y')
    except:
        L.append((str1, 1))
    else: L[idx] = (str1, L[idx][1] + 1)


>>> L = []
>>> str1 = 'hello'
>>> AddString(str1)
>>> L
[('hello', 1)]
>>> AddString(str1)
>>> L
[('hello', 2)]
>>> 

编辑

@JerseyMike:

谢谢,我很抱歉,我意识到问题不够清楚。在这个应用程序中;用户输入的是同一句话,就像在练习外语。所以输入将是

Hello world
Hello world
Hello world

如果用户接着输入“Hello universe”,那就会放到下一个列:

Hello world  Hello Universe
Hello world
Hello world

如果用户继续输入“Hello Universe”,它们应该放在同一列下面

Hello world  Hello Universe
Hello world  Hello Universe
Hello world  Hello Universe
             Hello Universe
             Hello Universe

包含这些内容的列表L看起来是这样的:

L = [
     ['Hello world', 'Hello Universe'], 
     ['Hello world', 'Hello Universe'], 
     ['Hello world', 'Hello Universe'], 
     ['',            'Hello Universe'], 
     ['',            'Hello Universe']
    ]

最开始列表是空的,我用L.append(s)添加字符串s

L = [
     ['Hello world'], 
     ['Hello world'], 
     ['Hello world'], 
    ]

如果最后一个字符串s与新的输入不匹配,我就用L[0].insert(1,s)创建新的列。

L = [
     ['Hello world', 'Hello Universe'], 
     ['Hello world'], 
     ['Hello world'], 
    ]             

现在我需要在'Hello Universe'下面写。这对我来说有几个原因很难弄明白。但现在我觉得在检查新字符串是否与之前的字符串相同之前,先把新的字符串s添加到列表中可能更好。为了简化列表,假设L是这样的:

L = [['A'], ['A'], ['A'], ['B']]

现在['B']需要插入到L[0]中。为此,我要向左搜索列表,找到最后一个只有1个元素的子列表(或者类似的东西)。我还没有研究过如何搜索列表。再次感谢你的帮助。

结束编辑


class Test(webapp.RequestHandler):
    myList = []
    def get(self):        
#        del self.myList[:]        
        s = [self.request.get('sentence')]
        r = len(self.myList)

        if r == 0: 
            self.myList.append(s)
            htmlcode1 = HTML.table(self.myList)
            lastItem = s  
        else:   
            if len(self.myList[0]) == 1:
                lastItem = self.myList[r-1]        
                if s == lastItem:
                    self.myList.append(s)             
                    htmlcode1 = HTML.table(self.myList)                
                else:
                    s = self.request.get('sentence') 
                    self.myList[0].insert(1,s)       
                    htmlcode1 = HTML.table(self.myList)
            if len(self.myList[0]) == 2:                
                    self.myList[1].insert(1,s)
                    htmlcode1 = HTML.table(self.myList)
            elif len(self.myList[1]) == 2:             
                    self.myList[2].insert(1,s)
                    htmlcode1 = HTML.table(self.myList)

        template_values = {'htmlcode1': htmlcode1,
                           's': s,
                           'r': r,
                           'myList': self.myList,
#                           'myListLen': myListLen,
                           'lastItem': lastItem,
                          }

        path = os.path.join(os.path.dirname(__file__), 'test.mako')
        templ = Template(filename=path)
        self.response.out.write(templ.render(**template_values))    

模板

<html>
<head>
</head>
<body>

<p>| <a href="/delete">CLEAR</a> |</p>

<form action="/test" method="get">
<input name="sentence" type="text" size="30"><br />
      <input type="submit" value="Enter">
</form>

<p>${htmlcode1}</p>
<p>s: ${s}</p>
<p>r: ${r}</p>
<p>myList: ${myList}</p>
<p>lastItem: ${lastItem}</p>

</html>
</body>

3 个回答

0

看起来你是在试图把所有东西都放进一个列表里,这样会让你的代码变得很难写。需要注意的是,你在列表里添加了空字符串('')来填充,这有点像是在告诉你,可能你的数据结构设计得不太对。

与其这样做,我建议你使用一个字典,字典的键可以是一个ID或者原始文本,然后把用户输入的内容存储为一个列表,最后再处理如何在代码的显示部分展示这些内容。可以参考下面的例子:

typing = {
    'Hello World': ['Hello World', 'Hello World', 'Hello World']
    'Hello Universe': ['Hello Universe', 'Hello Universe', 'Hello Universe', ...]
}

不过要记住,字典是无序的,所以你可能需要使用一个列表来排序,或者使用collections库里的sortedict。

0

如果我是你,我就不会使用嵌套列表。相反,应该使用字典。

字典的好处在于,你可以把一些键(也就是你想要每一行对应的字符串)和它们的值(在这个例子中,就是这些字符串出现的次数,或者说这一行在表格中的列数)对应起来。

所以,你可以这样做:

    def add_item(item, dict):
        if item in dict:
            dict[item] += 1
        else:
            dict[item] = 1

你可以通过使用 dict[string] 来引用表格中的单个字符串或行,看看这一行有多少列。

而且,使用字典比使用嵌套列表要简洁得多,节省内存,而且速度也更快。

如果你真的必须使用嵌套列表,告诉我,我会尽量帮你解决这个问题。

2

如果字符串的顺序很重要,那么用字典就不太合适了。你现在用列表的方向是对的,但我觉得你可能还需要更多的东西。老实说,我不太清楚你不同数据集的输出会是什么样子。如果我理解你的问题没错,下面的内容是否正确?

输入:

Sentence 1
Sentence 3
Sentence 1
Sentence 1
Sentence 2
Sentence 2

最后一行的输出:

Sentence 1 | Sentence 3 | Sentence 2
Sentence 1 |            | Sentence 2
Sentence 1 |            |

如果不是,请用一个例子重新描述你期望的输出。


好的,看起来我对你问题的理解是正确的。这是个不错的开始。;)

我觉得我们需要换个角度来看这个问题。目前,你把它看作是一个包含所有数据的大列表,可能这样有点太复杂了。我看到的是一个元组的列表,每个元组代表一列(字符串,计数)。这个元组会告诉我们这一列应该是什么字符串,以及有多少个。所以你的例子最终会变成这样:

L = [("Hello World", 3), ("Hello Universe", 5)]

我知道这并不是很明显该如何处理这些数据,但我认为这是内部表示的正确方式。我会给你一些示例代码,来进行一些基本的数据操作(其他人可能有更有效的方法来做到这一点)。

添加一个新的字符串:

def AddString(str):
try:
    idx = map(lambda (s, v): ('N', 'Y')[s == str], L).index('Y')
except:
    L.append( (str, 1) )
else:
    L[idx] = (str, L[idx][1] + 1)

打印HTML表格的内容:

def PrintChart():
try:
    max = reduce(lambda x, y: [x, y][x[1] < y[1]], L)[1]
except:
    print "<td></td>"
else:
    for i in range(max):
        print "<tr>"
        for (s, c) in L:
            if i+1 <= c:
                print "  <td" + s + "</td>"
            else:
                print "  <td></td>"
        print "</tr>"

总之,这就是我会做的方式。

撰写回答