1

我正在尝试创建一个执行以下操作的 python 脚本:

表(dbf 或 csv-我都可以创建)总是只有 4 条记录。第二列(Let)将始终按 a、b、c、d 排序。第 1 列(Num)总是有 0-10 之间的数字,但频率和顺序会有所不同。输出需要按 Num 排序和分组,首先输出最小的数字。如果第一列中的数字出现一次,则只输出对应的字母。如果一个数字出现两次(即两行具有相同的数字),则输出每个对应的字母,并在它们之间加上一个“和”。如果数字出现两次以上,则输出每个字母,它们之间有一个逗号,最后一个字母之前有一个“和”。出现的每个字母组都有自己的输出行。

基本上希望对 4 个选项中的 1 个进行排序、分组和输出:

“无数据”
1 个字母本身
2 个字母由“and”
分隔 3 个字母由逗号分隔,最后一个字母前有一个“and”。

以下是名为 soils_no.dbf 的表的各种版本及其所需的输出,具体取决于输入。

数字............让
0......a
0......b
0...... ..........c
0.......d
打印“无数据”

数字............让
8......a
8......b
2...... ..........c
8.......d
打印 c
打印 a、b 和 d

数字............让
4......a
1......b
7...... ..........c
3.......d
打印 b
打印 d
打印 a
打印 c

数字............让
3......a
3......b
10...... ..........c
1.......d
打印 d
打印 a 和 b
打印 c

数............让
10......a
10......b
10...... ..........c
10.................d
打印 a、b、c 和 d

我知道如何循环并将逗号和“和”放入,但我不知道如何分组和排序。使用 python 2.7 执行此操作。

顺便说一句,我正在尝试学习 python,所以请解释一下代码的含义。我学得越多,就越不依赖陌生人的善意。

提前致谢。

4

1 回答 1

1

下面讨论。

from collections import defaultdict

def pretty_print_lst(lst):
    if not lst:
        return ""
    elif len(lst) == 1:
        return lst[0]
    elif len(lst) == 2:
        # Join together two letters using " and " as the join.
        return " and ".join(lst)
    else:
        # Use a "list slice" to join all in the list but the last item,
        # using ", " as the join, then append " and " and append the
        # last item.  Last item is indexed with -1, which always works no
        # matter how many or few items are in the list.
        return ", ".join(lst[:-1]) + " and " + lst[-1]

def print_rec(seq):
    # group according to counts
    d = defaultdict(list)
    for row in seq:
        n, letter = row  # get count and letter from the row
        d[n] += letter  # append letter to that count list

    # get a list of (key, value) pairs
    # so the list entries are: (count, list_of_letters)
    results = list(d.items())
    results.sort()
    if len(results) == 1 and results[0][0] == 0:
        # if all 4 letters have a count of 0, 
        print("No data")
    else:
        for count, lst in results:
            s = pretty_print_lst(lst)
            print(s)

lst = [ (8, 'a'), (8, 'b'), (2, 'c'), (8, 'd')]
print_rec(lst)

我们使用字典来收集具有相同计数的项目。这是一个“默认字典”;每当我们引用一个不存在的键时,它就会被创建,在这种情况下是一个空列表。所以我们可以只附加值,字典是否为空都没有关系。

然后我们收集非零项目并制作一个列表,然后漂亮地打印列表以匹配您想要的格式。

如果您有任何问题,请随时提问。

于 2013-02-28T01:47:23.957 回答