【问题标题】:Count items in dictionary计算字典中的项目
【发布时间】:2015-02-21 19:06:03
【问题描述】:

我需要计算不同的 IDENTIFIERS 并为它们打印一个数字。信息来自如下所示的数据流:

                             IDENTIFIER
7756753.940 receivetest: m s 0x0000069a 8 00 00 00 00 00 e4 8a 9a 
7756754.409 receivetest: m s 0x00000663 8 2f 00 62 02 00 e4 8a 9a 
7756754.878 receivetest: m s 0x0000069e 8 00 1f 5e 28 34 83 59 1a 
7756755.348 receivetest: m s 0x00000690 8 00 18 00 28 34 83 59 1a 
7756853.908 receivetest: m s 0x0000069a 8 00 00 00 00 00 e4 8a 9a 
7756854.377 receivetest: m s 0x0000069e 8 00 1f 5e 28 34 83 59 1a 
7756854.846 receivetest: m s 0x00000663 8 2f 00 62 02 00 e4 8a 9a 
7756855.316 receivetest: m s 0x00000690 8 00 18 00 28 34 83 59 1a 
7756953.961 receivetest: m s 0x0000069a 8 00 00 00 00 00 e4 8a 9a 
7756954.430 receivetest: m s 0x00000663 8 2f 00 62 02 00 e4 8a 9a 
7756954.857 receivetest: m s 0x0000069e 8 00 1f 5e 28 34 83 59 1a 
7756955.326 receivetest: m s 0x00000690 8 00 18 00 28 34 83 59 1a 
7757053.929 receivetest: m s 0x0000069a 8 00 00 00 00 00 e4 8a 9a 
7757054.398 receivetest: m s 0x00000663 8 2f 00 62 02 00 e4 8a 9a 
7757054.868 receivetest: m s 0x0000069e 8 00 1f 5e 28 34 83 59 1a 
7757055.337 receivetest: m s 0x00000690 8 00 18 00 28 34 83 59 1a 
7757153.940 receivetest: m s 0x0000069a 8 00 00 00 00 00 e4 8a 9a 
7757154.409 receivetest: m s 0x00000663 8 2f 00 62 02 00 e4 8a 9a 
7757154.878 receivetest: m s 0x0000069e 8 00 1f 5e 28 34 83 59 1a 
7757155.348 receivetest: m s 0x00000690 8 00 18 00 28 34 83 59 1a 
7757227.369 receivetest: m s 0x00000688 8 00 00 00 00 00 00 00 00 

这是我的代码:

#!/usr/bin/python

import subprocess
import re, os, pprint

DICT = {}

def RECEIVE(COMMAND):
    PROCESS = subprocess.Popen(COMMAND, stdout=subprocess.PIPE)
    LINES = iter(PROCESS.stdout.readline, "")
    for LINE in LINES:
        if re.match(r"^\d+.*$",LINE):
            SPLITLINE = LINE.split()
            del SPLITLINE[1:4]
            TIMER = SPLITLINE[0]
            IDENTIFIER = SPLITLINE[1]
            DLC = SPLITLINE[2]
            HEXBITS = SPLITLINE[3:]
            COUNTER = DICT.count(IDENTIFIER)
            DICT[IDENTIFIER] = [DLC, HEXBITS, TIMER[6:], COUNTER]
            for IDENTIFIER, HEXBITS in DICT.items():
                os.system("clear")
                pprint.pprint(DICT)

RECEIVE(["receivetest", "-f=/dev/pcan33"])

我只需要打印任何给定 IDENTIFIER 被读取的次数

【问题讨论】:

  • 还有什么问题?代码不起作用吗?有什么错误吗?
  • 请使用Python code style 变量和方法名不要使用大写字母
  • 计数器不计算每个标识符被读取的次数,如果打印时也不显示任何内容
  • 您想要总次数,还是每次接收时更新的运行计数器?
  • 我很惊讶当你尝试运行它时它没有抛出错误。我不认为count 是 Python 字典的可行方法。

标签: python dictionary counter data-stream can-bus


【解决方案1】:

您可以使用collections.Counter,但对于这种情况,collections.defaultdict 就足够了:

from collections import defaultdict

def RECEIVE(COMMAND):
    counts = defaultdict(int)

    # <your code>
    IDENTIFIER = SPLITLINE[1]
    counts[IDENTIFIER] += 1
    # <rest of your code>

    # <whenever you want to see how many times some identifier has appeared>
    print(counts[SOME_IDENTIFIER])

【讨论】:

  • 如果我想要一个标识符的计数但我想要每个标识符的计数,这很好
  • 这将保持每个标识符出现的次数。您可以查询您选择的任何标识符,它将打印该标识符出现了多少次。如果该标识符根本没有出现,将打印0
  • @Jalcock501 当你的所有输入都输入完毕后,执行for (id, count) in counts.items(): print(id, count) 之类的操作(我从你的代码中推断你在 Python 3.x 中?)
  • @rchang 输入永远不会停止它是一个恒定的流并且没有 python 2.7.3
【解决方案2】:

当然,您可以使用简单的 gnu 工具,例如

receivetest -f=/dev/pcan33 | cut -f 5 | uniq | wc -l

但是如果你坚持使用python...

identifiers = set(line.split()[4] for line in lines)

【讨论】:

    【解决方案3】:

    如果你只是想要一个字典来计算对象,你可以这样做:

    id_count = {}
    def recieve():
        # insert your subprocess and read here, change the loop
        for line in identifiers.split('\n'):
        if re.match(r"^\d+.*$",line):
            identifier = line.split()[4]
            if identifier in id_count.keys():
                id_count[identifier] += 1
            else:
                id_count[identifier] = 1
    

    之后,您可以打印或访问 dict 以查看您收到每个标识符的次数

    【讨论】:

      【解决方案4】:
      >>> DICT = {}
      >>> for LINE in LINES:
      ...   SPLITLINE = LINE.split()
      ...   try:
      ...      DICT[SPLITLINE[4]] = DICT[SPLITLINE[4]] + 1
      ...   except:
      ...      DICT[SPLITLINE[4]] = 1
      ... 
      >>> DICT
      {'0x0000069a': 5, '0x00000690': 5, '0x00000688': 1, '0x00000663': 5, '0x0000069e': 5}
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2023-04-10
        • 2011-03-30
        • 2021-11-15
        • 1970-01-01
        • 2022-11-15
        • 1970-01-01
        相关资源
        最近更新 更多