【问题标题】:Better way to do string filtering/manipulation进行字符串过滤/操作的更好方法
【发布时间】:2009-10-18 11:23:22
【问题描述】:

我的字符串 = '14| "预处理器帧数不递增;卡:主板,端口:2"|minor'

所以我有 3 个元素(id、message 和 level)除以管道(“|”)。我想获取每个元素,所以我写了这些小函数:

    def get_msg(i):
        x = i.split("|")
        return x[1].strip().replace('"','')

    def get_level(i):
        x = i.split("|")
        return x[2].strip()
 #testing
print get_msg(mystring ) # Missing Input PID,   PID: 20 : Port 4 of a static component
print get_level(mystring )# major

现在效果很好,但我觉得这不是pythonic的解决方法,这两个功能如何改进?正则表达式在这里感觉很合适,但我很天真所以无法应用。

【问题讨论】:

  • 实际上,拆分可能是解决此问题的好方法。正则表达式可能会矫枉过正。您可能只是将 " 作为要剥离() 的字符之一,而不是使用 replace()。

标签: python string


【解决方案1】:

我认为最 Pythonic 的方式是使用 csv 模块。 来自PyMotW,带有分隔符选项:

import csv
import sys

f = open(sys.argv[1], 'rt')
try:
    reader = csv.reader(f, delimiter='|')
    for row in reader:
        print row
finally:
    f.close()

【讨论】:

    【解决方案2】:
    lst = msg.split('|')
    level = lst[2].strip()
    message = lst[1].strip(' "')
    

    您将字符串拆分两次,这有点浪费,除了修改很小。

    【讨论】:

      【解决方案3】:
      class MyParser(object):
          def __init__(self, value):
              self.lst = value.split('|')
          def id(self):
              return self.lst[0]
          def level(self):
              return self.lst[2].strip()
          def message(self):
              return self.lst[1].strip(' "')
      

      【讨论】:

      • 不错 - 与我的哈希图一样。
      【解决方案4】:

      我认为最好的做法是实际使用格式更好的字符串,或者不使用字符串。为什么是字符串?你从哪里解析这个?数据库? Xml?原产地可以改吗?

      { 'id': 14, 'message': 'foo', 'type': 'minor' }
      

      我认为像这样的数据类型是最佳实践,如果它存储在数据库中,然后将其拆分为多个列。

      编辑:我可能会为此感到震惊,因为它可能是矫枉过正/效率低下,但如果你稍后添加很多部分,你可以将它们存储在一个不错的哈希图中:

      >>> formatParts = {
      ...     'id': lambda x: x[0],
      ...     'message': lambda x: x[1].strip(' "'),
      ...     'level': lambda x: x[2].strip()
      ... }
      >>> myList = mystring.split('|')
      >>> formatParts['id'](myList)
      '14'
      >>> formatParts['message'](myList)
      'Preprocessor Frame Count Not Incrementing; Card: Motherboard, Port: 2'
      >>> formatParts['level'](myList)
      'minor'
      

      【讨论】:

      • 它是从我使用 commands.getstatusoutput() 获取的 shell 脚本的输出中解析出来的,这正是我检索字符串的方式。
      • 我认为问题在于你仍然在做同样的事情来获取这些元素,但是你在晦涩的函数调用后面隐藏了一个常规操作
      【解决方案5】:

      如果您不需要 getter 函数,这应该可以很好地工作:

      >>> m_id,msg,lvl = [s.strip(' "') for s in mystring.split('|')]
      >>> m_id,msg,lvl
      ('14', 'Preprocessor Frame Count Not Incrementing; Card: Motherboard, Port: 2',
      'minor')
      

      注意:避免遮蔽内置函数“id”

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2010-12-04
        • 2012-05-31
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多