Python - 去重字典键

1 投票
2 回答
547 浏览
提问于 2025-04-15 18:22

我有一些数据是从机器上获取的(通过pexpect),然后我用正则表达式把这些数据解析成一个字典,像这样:

for line in stream:
    if '/' in line:
        # some matching etc which results in getting the
        # machine name, an interface and the data for that interface
        key=str(hostname)+":"+r.groups()[0][0:2]+r.groups()[2]
        dict[key]=str(line[3])

这一切都运行得不错,当我读取数据时,会得到很多这样的行:

machine1:fe0 <data>  

<data> 是一个字符串或整数。

我现在意识到,对于这个接口可能会有多个数据,而在这种情况下,每次遇到相同的键时,我都会覆盖之前的值。我希望能让这个键变得独特,以便能突出显示该接口有多个信息。例如,如果 fe0 有 3 个实例,或者 fe1 有 4 个。

machine1:fe0:3 <data> <data> <data>
machine1:fe1:4 <data> <data> <data> <data>

为此,我不介意如果单个实例后面加个 1 来告诉我这一点。
希望这样说清楚了,也希望有人能给我指个方向,非常感谢!

2 个回答

0
for (lineno, line) in enumerate(stream):
    if '/' in line:
        # some matching etc which results in getting the
        # machine name, an interface and the data for that interface
        key=str(hostname)+":"+r.groups()[0][0:2]+r.groups()[2]
        dict[key + ":" + lineno]=str(line[3])

这样做的话,虽然不会让数字平滑地增加,但每个字典的键都是独一无二的,而且和每个主机名加接口的组合对应的数字会逐渐增大。你可以通过把最后一行改成 dict[key + ":" + ('%06d' % (lineno,))=str(line[3]) 来让这些键可以按字母顺序排序。

4

你可以为每个键创建一个列表,里面存放该键的所有值:

d = collections.defaultdict(list)
for line in stream:
    if '/' in line:
        #.....
        key =  str(hostname)+":"+r.groups()[0][0:2]+r.groups()[2]
        value = str(line[3])
        d[key].append(value)

补充:如果你想要的键和值和你问题中提到的一样,你可以这样做:

d2 = {}
for key,values in d.iteritems():
    d2['%s:%d' % (key, len(values)] = ' '.join(str(v) for v in values)

我在这里用了 ' '.join() 来把这些值合并成一个字符串——从你的问题来看,不太清楚你是否想要这样。

我不建议这样做,因为这样会让你获取单个值变得更困难。

撰写回答