【问题标题】:how do I convert a string to a valid variable name in python?如何在 python 中将字符串转换为有效的变量名?
【发布时间】:2011-03-19 05:08:19
【问题描述】:

我需要将任意字符串转换为在 python 中是有效变量名的字符串。

这是一个非常基本的例子:

s1 = 'name/with/slashes'
s2 = 'name '

def clean(s):
    s = s.replace('/','')
    s = s.strip()
    return s

print clean(s1)+'_'#the _ is there so I can see the end of the string

这是一种非常幼稚的方法。我需要检查字符串是否包含无效 变量名字符并将其替换为 ''

pythonic 的方法是什么?

【问题讨论】:

  • 你想用这个方法解决什么问题?可能有更好的方法。
  • print repr("a string ") 在引号中显示字符串 - 比在其上附加 _ 更简洁。
  • 我正在遍历来自 Cinema 4d 的场景图,需要在搅拌机中重新创建它。为了让我更容易理解,我想使用cinema4d对象的实际名称作为Blender Python的变量名,所以我需要先调整这些

标签: python validation string variables


【解决方案1】:

您应该构建一个允许字符白名单的正则表达式,并替换不在该字符类中的所有内容。

【讨论】:

  • 或者更好的是,建立一个允许字符串的白名单并将它们链接到实际的预定义对象。每次出现此类问题时,我都会感到紧张,并认为几乎可以肯定有人要编写一个巨大的安全漏洞。
  • :) 不是我...我只是在解析来自 Cinema 4d 的场景图,需要在搅拌机中重新创建它。动画师通常不担心或不需要担心对象名称中的空格/斜线/等
【解决方案2】:

使用 re 模块,去掉所有无效字符。

【讨论】:

    【解决方案3】:

    According to Python,标识符是一个字母或下划线,后跟无限的字母、数字和下划线字符串:

    import re
    
    def clean(s):
    
       # Remove invalid characters
       s = re.sub('[^0-9a-zA-Z_]', '', s)
    
       # Remove leading characters until we find a letter or underscore
       s = re.sub('^[^a-zA-Z_]+', '', s)
    
       return s
    

    这样使用:

    >>> clean(' 32v2 g #Gmw845h$W b53wi ')
    'v2gGmw845hWb53wi'
    

    【讨论】:

    • +1 用于识别第一个字母与后续字母的有效字符不同,以及仅允许有效字母与去除无效字母。
    • @JukkaSuomela 有一个很好的观点。由于所有保留的关键字都是字母,所以可以通过加下划线来保证不冲突(如果你想真正的好,可以先检查名字是否是关键字,如果是的话只加下划线)案例)。
    • 您可以使用“keyword”模块确保名称不与任何 Python 关键字冲突,“keyword.iskeyword(s)”
    【解决方案4】:

    好吧,我想最好的 Triptych 的解决方案是......单线!

    >>> def clean(varStr): return re.sub('\W|^(?=\d)','_', varStr)
    ...
    
    >>> clean('32v2 g #Gmw845h$W b53wi ')
    '_32v2_g__Gmw845h_W_b53wi_'
    

    此替换用下划线替换任何不可变的适当字符,如果字符串以数字开头,则在前面插入下划线。 IMO,'name/with/slashes' 作为变量名 name_with_slashes 看起来比 namewithslashes 更好。

    【讨论】:

    • 如果您想将多个无效字符折叠成一个_,请使用以下命令:re.sub(r'\W+|^(?=\d)','_', varStr)(在非单词字符\W 之后添加+ 符号)跨度>
    • 请不要使用lambda 来定义“命名”函数。它带来了多个问题。 lambda 用于其他用途。如果您坚持在一行中编写代码 - 在这种情况下您可以轻松完成:def clean(varStr): return re.sub('\W|^(?=\d)','_', varStr) --- 否则我同意替换无效字符通常比删除它们更好。
    • @pabouk 我想我的意思是展示它是一个单一的表达式 - 但可以肯定,def 它是
    【解决方案5】:

    您可以将内置的 func:str.isidentifier()filter() 结合使用。 这不需要诸如re 之类的导入,并且通过迭代每个字符并在其为标识符时返回它来工作。然后你只需执行 ''.join 再次将数组转换为字符串。

    s1 = 'name/with/slashes'
    s2 = 'name '
    
    def clean(s):
        s = ''.join(filter(str.isidentifier, s))
        return s
    
    print f'{clean(s1)}_' #the _ is there so I can see the end of the string
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2012-09-27
      • 1970-01-01
      • 2022-08-11
      • 1970-01-01
      • 2012-02-25
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多